home *** CD-ROM | disk | FTP | other *** search
/ Gekkan Dennou Club 147 / Gekkan Dennou Club - 2000.8 Vol. 147 (Japan).7z / Gekkan Dennou Club - 2000.8 Vol. 147 (Japan) (Track 1).bin / tools / ask / askden / source / askden2.s < prev    next >
Text File  |  1999-04-05  |  80KB  |  3,600 lines

  1. ******************************************************************************
  2. *    ASK3アクセサリ  ASKDen  V2.02
  3. *        Copyright 1998-99 by AIG-Soft
  4. ******************************************************************************
  5.  
  6.     .include    defines.mac
  7.     .include    fefunc.mac    * 整数/実数演算を使う
  8.     .include    pspdef.mac
  9.     .include    ask3.mac
  10.     .cpu        68000
  11.  
  12. ******************************************************************************
  13. *    常駐ルーチン
  14. ******************************************************************************
  15. * 年号をわざわざテキストでなしにバイナリー化しているのは、テキストのみより
  16. * 誤った一致をしにくいから
  17.  
  18.     .text
  19.     .even
  20. KEEP_START:
  21. varad    .dc.l    0    * varのアドレスが入る(Den2Var用)
  22.     * 常駐確認用識別子
  23. id:    .dc.b    'ASKDen V2.02',19,99,'AIG-Soft',0
  24.  
  25. ******************************************************************************
  26. * 定数表
  27. ******************************************************************************
  28.  
  29. ACCS    equ    2        * 全アクセサリの数
  30. BMAX    equ    4        * basesの個数
  31. *
  32. FeMin    equ    $fe00        * FLOAT?.Xのコールコード最小値
  33. Yuketa    equ    6        * 32ビット単精度実数の有効桁数
  34.                 * 実験の結果より6桁なら大丈夫らしい
  35. * 変数関係
  36. VTYPE    equ    %1_1111        * 変数型(32種類)
  37. VKAKU    equ    BIT7        * 0=確定 , 1=未確定
  38. VDAI    equ    BIT6        * 0=再代入可 , 1=不可
  39. BVDAI    equ    6        * VDAIのビット番号
  40. V_INT    equ    0        * 0=整数数値(すべての演算可能)
  41. V_FLOAT    equ    1        * 1=単精度実数
  42. *
  43. VTOP    equ    2        * 変数格納先頭位置:ハッシュの関係で0は使えない
  44. *
  45. * 演算子内部コード
  46. VMINUS    equ    '@'        * マイナス
  47. VRSHIFT    equ    (('>'<<8)|'>')    * 右シフト
  48. VLSHIFT    equ    (('<'<<8)|'<')    * 右シフト
  49. VGE    equ    (('>'<<8)|'=')    * 大なりイコール
  50. VLE    equ    (('<'<<8)|'=')    * 小なりイコール
  51. VEQU    equ    (('='<<8)|'=')    * イコール
  52. VNE    equ    (('!'<<8)|'=')    * not イコール
  53. VRROT    equ    (('-'<<8)|'>')    * 右ローテート
  54. VLROT    equ    (('<'<<8)|'-')    * 右ローテート
  55. VINC    equ    (('+'<<8)|'+')    * +1
  56. VDEC    equ    (('-'<<8)|'-')    * -1
  57. VBEKI    equ    (('*'<<8)|'*')    * べき乗
  58. VAND    equ    (('&'<<8)|'&')    * 論理AND
  59. VOR    equ    (('|'<<8)|'|')    * 論理OR
  60.  
  61. * 式系のエラー
  62. VSNONE        equ    1    * 数値/変数がない
  63. VSDBL        equ    2    * DouBLe 数値/変数が2つ続いている
  64. VSOEN        equ    3    * Only Enzan 演算子のみ
  65. VSILL        equ    4    * ILLegal 式がおかしい
  66. VSCPXS        equ    5    * ComPleX Suuti 式が複雑すぎる(数値/変数)
  67. VSCPXE        equ    6    * ComPleX Enzan 式が複雑すぎる(演算子)
  68. VSCPXC        equ    7    * ComPlex C 式が複雑すぎる(括弧)
  69. VSCNONE        equ    8    * (がない
  70. VSENONE        equ    9    * (の前に演算子がない
  71. VSNNONE        equ    10    * Naka NONE ()内がない
  72. VSCILL        equ    11    * ()内の式がおかしい
  73. VSCNENG        equ    12    * Not Enough )が足りない
  74. VSNUMST        equ    13    * Num STore 数値に代入しようとした
  75. VSCHERR        equ    14    * 文字コードが'で括られていない
  76. VSNOFILE    equ    15    * 式ファイルが見つからない(ASKDen)
  77. VSLONG        equ    16    * 式が長すぎる(ASKDen)
  78. VSIONLY        equ    17    * 整数モードでしか使えない(ASKDen2)
  79. VSFONLY        equ    18    * 実数モードでしか使えない(ASKDen2)
  80. VS0DIV        equ    20    * 0で除算した
  81. VSOVER        equ    21    * オーバーフロー
  82. VSUNDER        equ    22    * アンダーフロー
  83. VSARG        equ    23    * 引数がおかしい
  84.  
  85. * 変数系のエラー
  86. VARNDEF        equ    50    * No Define 変数が未定義
  87. VARNST        equ    51    * No STore  未確定変数への代入がない
  88. VAROST        equ    52    * Only STore 未確定変数には代入しか出来ない
  89. VARLONG        equ    53    * 変数名が長すぎ
  90. VAROVER        equ    54    * 変数はこれ以上定義出来ない
  91. VARNMEM        equ    55    * 変数処理用メモリーが足りない
  92. VARNKAKU    equ    56    * No KAKUtei 変数が未確定
  93. VARDBL        equ    57    * 変数が2重定義された
  94. VARILL        equ    58    * 変数名が異常
  95. VARCSTA        equ    59    * Can't STore Again 再代入不可変数に代入しようとした
  96. VARTYPE        equ    60    * 変数の型が違う
  97. VARNAC        equ    61    * 未確定変数にアクセスした
  98. VARNKAKUR    equ    62    * No KAKUtei Remain 未確定変数が残っている
  99. VARAROVER    equ    63    * 変数エリアを越えている
  100. VARCCINT    equ    64    * Can't Convert INTeger 整数化出来ない
  101. * <128なのでmoveq.lで代入出来る
  102. ******************************************************************************
  103. * ワーク1
  104. ******************************************************************************
  105. * このワークエリアは起動時に初期値が必要/初期化時に利用するものである。
  106. *
  107.     .even
  108. ACh        .dcb.l    ACCS,-1    * アクセサリ(初期値-1<0)
  109.                 * 正常登録された時、ACh[]>=0になる(0,1,2,3...)
  110. all        .dc.l    0    * 全ワークエリアサイズ
  111.  
  112. bases        .dc.b    10,16,2,8    * 進数テーブル(良く使う順)
  113. base:        .dc.w    0        * 10進数(bases[base])
  114.  
  115. hugo        .dc.b    $ff    * 0=符号なし,$ff=符号有り
  116. fhigh        .dc.b    0    * 0=低位メモリー確保,$ff=高位メモリー確保
  117. first        .dc.b    1    * 0=No,1=Yes,$ff=エラー発生直後
  118. ffloat        .dc.b    0    * 0=32bit整数,$ff=単精度実数
  119. fnai        .dc.b    0    * 0=整数化,$ff=内部表現
  120. fzen        .dc.b    0    * 0=半角出力,$ff=全角出力
  121. ftei        .dc.b    0    * 0=普通変数、$ff=定数(起動時式ファイル)
  122. *
  123. preexecI    .ds.b    90    * 整数 式ファイル名
  124. preexecF    .ds.b    90    * 実数 式ファイル名
  125.         .even
  126.  
  127. fsizeI        .dc.l    -1    * 整数 式ファイルチェック用
  128. fdateI        .dc.w    -1    *
  129. ftimeI        .dc.w    -1    *
  130. *
  131. fsizeF        .dc.l    -1    * 整数 式ファイルチェック用
  132. fdateF        .dc.w    -1    *
  133. ftimeF        .dc.w    -1    *
  134.  
  135. * 構造体;実体
  136. Vsikis        * 式構造体
  137.         .dc.w    30    *0  short emax
  138.         .dc.w    30    *2  short vmax
  139.         .dc.w    0    *4  short es
  140.         .dc.w    0    *6  short vs
  141.         .ds.l    1    *8  unsint *estack
  142.         .ds.l    1    *12 long/float *vstack
  143.         .ds.l    1    *16 long *pstack
  144. *
  145. var        * 変数構造体
  146.         .dc.l    0    *0  unchar *vwork    ワークエリア先頭アドレス(初期値は0=確保してない)
  147.         .ds.l    1    *4  long vwsize
  148.         .dc.l    2    *8  long vpoint        変数格納先頭位置:ハッシュの都合で0は使えない
  149.         .dc.l    0    *12 long vlots
  150.         .ds.l    1    *16 long *vhash
  151.         .ds.w    1    *20 unsint vhsize
  152.         .dc.w    32    *22 unsint vlmax    変数名最大長
  153.         .dc.w    0    *24 unsint mode
  154.         .even
  155.  
  156. ******************************************************************************
  157. * オフセット表
  158. ******************************************************************************
  159. * オフセットで書かれている部分もあれば即値で書かれている部分もあるので変更しないこと。
  160.  
  161. * 構造体;オフセット表
  162.     .offset    0
  163. * 変数構造体
  164. vwork        .ds.l    1    * unchar *vwork
  165. vwsize        .ds.l    1    * long vwsize
  166. vpoint        .ds.l    1    * long vpoint
  167. vlots        .ds.l    1    * long vlots
  168. vhash        .ds.l    1    * long *vhash
  169. vhsize        .ds.w    1    * unsint vhsize
  170. vlmax        .ds.w    1    * unsint vlmax
  171. mode        .ds.w    1    * unsint mode
  172.  
  173.     .offset    0
  174. * 式構造体
  175. emax        .ds.w    1    * short emax
  176. vmax        .ds.w    1    * short vmax
  177. es        .ds.w    1    * short es
  178. vs        .ds.w    1    * short vs
  179. estack        .ds.l    1    * unsint *estack
  180. vstack        .ds.l    1    * long/float *vstack
  181. pstack        .ds.l    1    * long *pstack
  182.  
  183.     .offset    0
  184. * 変数格納オフセット
  185. *    len mode num name[00]
  186. *    1   1    4   len+1        size
  187. *    0   1    2   6        6+len+1    offset
  188. Vlen        .ds.b    1
  189. Vmd        .ds.b    1
  190. Vnum        .ds.l    1
  191. Vname
  192.     .text
  193. sizeV    equ    Vname        * len+mode+numのサイズ
  194.  
  195. ******************************************************************************
  196. * メッセージ
  197. ******************************************************************************
  198.  
  199. Title        .dc.b    '+00進/整数 ',0
  200. *             01234567890     ← 一部書き換わる
  201. *             0=+/-(符号) , 12=10/02/16/08 , 67=整/実 , 10=' '/*:実数内部表現
  202. MesError    .dc.b    ':',0
  203.  
  204. * var_dumpで利用
  205. CrLf2:        .dc.b    CR,LF,0
  206. MesMikaku:    .dc.b    '[未確定]',0    * 今のバージョンでは仮確定するから出ないはずだけど
  207. MesTeisu:    .dc.b    '[定数]',0
  208. MesDeni:    .dc.b    '整数',0    * 起動メッセージでも使う
  209. MesDenf:    .dc.b    '実数',0    * 起動メッセージでも使う
  210. Bsym        .dc.b    ' $%@',0    * 進数シンボル(baseの順)
  211.  
  212. *---------------------------------------------
  213. * エラーメッセージ群
  214. *---------------------------------------------
  215. * 使われていないエラーメッセージもあるかも
  216. *
  217. InErr        .dc.b    '内部エラー;ご連絡下さい',0
  218. ERRmes:
  219. MVSNONE:    .dc.b    '数値/変数がない',0
  220. MVSDBL:        .dc.b    '数値/変数が2つ続いている',0
  221. MVSOEN:        .dc.b    '演算子のみ',0
  222. MVSILL:        .dc.b    '式が異常',0
  223. MVSCPXS:    .dc.b    '式が複雑すぎる(数値/変数)',0
  224. MVSCPXE:    .dc.b    '式が複雑すぎる(演算子)',0
  225. MVSCPXC:    .dc.b    '式が複雑すぎる(括弧)',0
  226. MVSCNONE:    .dc.b    '(がない',0
  227. MVSENONE:    .dc.b    '(の前に演算子がない',0
  228. MVSNNONE:    .dc.b    '()内がない',0
  229. MVSCILL:    .dc.b    '()内の式が異常',0
  230. MVSCNENG:    .dc.b    ')が足りない',0
  231. MVSNUMST:    .dc.b    '数値に代入しようとした',0
  232. MVSCHERR:    .dc.b    '文字コードが',$27,'で括られていない',0
  233. MVSNOFILE:    .dc.b    '式ファイルが見つからない',0
  234. MVSLONG:    .dc.b    '式が長すぎる',0
  235. MVSIONLY    .dc.b    '整数モードでしか使えない',0    * float
  236. MVSFONLY    .dc.b    '実数モードでしか使えない',0    * float
  237. MVS0DIV        .dc.b    '0で除算した',0
  238. MVSOVER        .dc.b    'オーバーフロー',0
  239. MVSUNDER    .dc.b    'アンダーフロー',0
  240. MVSARG        .dc.b    '引数がおかしい',0
  241. *
  242. MVARNDEF:    .dc.b    '変数が未定義',0
  243. MVARNST:    .dc.b    '未確定変数への代入がない',0
  244. MVAROST:    .dc.b    '未確定変数には代入しか出来ない',0
  245. MVARLONG:    .dc.b    '変数名が長すぎる',0
  246. MVAROVER:    .dc.b    '変数はこれ以上定義出来ない',0
  247. MVARNMEM:    .dc.b    '変数処理メモリーが足りない',0
  248. MVARNKAKU:    .dc.b    '変数が未確定',0
  249. MVARDBL:    .dc.b    '変数が2重定義された',0
  250. MVARILL:    .dc.b    '変数名が異常',0
  251. MVARCSTA:    .dc.b    '定数に代入する',0    * 再代入不可変数
  252. MVARTYPE:    .dc.b    '変数の型が違う',0
  253. MVARNAC:    .dc.b    '未確定変数にアクセスした',0
  254. MVARNKAKUR:    .dc.b    '未確定変数が残っている',0
  255. MVARAROVER:    .dc.b    '変数エリアを越える',0
  256. MVARCCINT    .dc.b    '整数化出来ない',0
  257.     .even
  258.  
  259. *---------------------------------------------
  260. * エラーコード表(上のメッセージと同じ順)
  261. *---------------------------------------------
  262.  
  263. ERRvsiki:
  264.     .dc.w    VSNONE,VSDBL,VSOEN,VSILL,VSCPXS,VSCPXE,VSCPXC,VSCNONE,VSENONE,VSNNONE
  265.     .dc.w    VSCILL,VSCNENG,VSNUMST,VSCHERR,VSNOFILE,VSLONG
  266.     * 実数版で追加
  267.     .dc.w    VSIONLY,VSFONLY,VS0DIV,VSOVER,VSUNDER,VSARG
  268.     *
  269.     .dc.w    VARNDEF,VARNST,VAROST,VARLONG,VAROVER,VARNMEM,VARNKAKU,VARDBL,VARILL
  270.     .dc.w    VARCSTA,VARTYPE,VARNAC,VARNKAKUR,VARAROVER,VARCCINT
  271.     * EOT
  272.     .dc.w    0
  273.     .even
  274.  
  275. *---------------------------------------------
  276. * 演算子
  277. *---------------------------------------------
  278. * 文字列,0=両方,1=整数のみ,2=floatのみ
  279. * 同じ文字列で始まる場合、長い物から先に記述する
  280. ENmes:
  281. ?C0:    .dc.b    '(',0
  282. ?C1:    .dc.b    ')',0
  283. ?C2:    .dc.b    '++',0
  284. ?C3:    .dc.b    '--',0
  285. ?C5:    .dc.b    '==',0
  286. ?C6:    .dc.b    '>>>',1
  287. ?C7:    .dc.b    '<<<',1
  288. ?C8:    .dc.b    '>>',1
  289. ?C9:    .dc.b    '<<',1
  290. ?C10:    .dc.b    '>=',0
  291. ?C11:    .dc.b    '<=',0
  292. ?C12:    .dc.b    '>',0
  293. ?C13:    .dc.b    '<',0
  294. ?C14:    .dc.b    '!=',0
  295. ?C15:    .dc.b    '+',0
  296. ?C16:    .dc.b    '-',0
  297. ?C99:    .dc.b    '**',2        * べき乗(power)
  298. ?C17:    .dc.b    '*',0
  299. ?C18:    .dc.b    '/',0
  300. ?C98:    .dc.b    '&&',0
  301. ?C19:    .dc.b    '&',1
  302. ?C97:    .dc.b    '||',0
  303. ?C20:    .dc.b    '|',1
  304. ?C21:    .dc.b    '^',1
  305. ?C22:    .dc.b    '~',1
  306. ?C23:    .dc.b    '\',0
  307. ?C24:    .dc.b    '=',0
  308. ?C96:    .dc.b    '!',0
  309. * 以下関数(べき乗だけは2項関数なので上の演算子にする)
  310. * 英小文字
  311. ?ABS:    .dc.b    'abs',2        * 絶対値
  312. ?CEIL:    .dc.b    'ceil',2    * 小数切上
  313. ?FIX:    .dc.b    'fix',2        * 整数部
  314. ?FLOOR:    .dc.b    'floor',2    * 小数切捨
  315. ?FRAC:    .dc.b    'frac',2    * 小数部
  316. ?SGN:    .dc.b    'sgn',2        * 正負零
  317. ?EXP:    .dc.b    'exp',2        * 指数関数
  318. ?SQR:    .dc.b    'sqr',2        * 平方根
  319. ?PI:    .dc.b    'pi',2        * 円周率乗算
  320. ?LOG10:    .dc.b    'log10',2    * 常用対数
  321. ?LOG2:    .dc.b    'log2',2    * 対数(底2)
  322. ?LOG:    .dc.b    'log',2        * 自然対数
  323. ?SIN:    .dc.b    'sin',2        * 正弦
  324. ?COS:    .dc.b    'cos',2         * 余弦
  325. ?TAN:    .dc.b    'tan',2        * 正接
  326. ?ATANH:    .dc.b    'atanh',2    * 双曲逆正接
  327. ?ASIN:    .dc.b    'asin',2    * 逆正弦
  328. ?ACOS:    .dc.b    'acos',2    * 逆余弦
  329. ?ATAN:    .dc.b    'atan',2    * 逆正接
  330. ?SINH:    .dc.b    'sinh',2    * 正弦
  331. ?COSH:    .dc.b    'cosh',2    * 双曲余弦
  332. ?TANH:    .dc.b    'tanh',2    * 双曲正接
  333.     .even
  334.  
  335. *---------------------------------------------
  336. * 演算子テーブル(上の演算子表と同じ順)
  337. *---------------------------------------------
  338. * 内部コード
  339. enzansi:
  340.     .dc.w    '(',')',VINC,VDEC,VEQU
  341.     .dc.w    VRROT,VLROT,VRSHIFT,VLSHIFT
  342.     .dc.w    VGE,VLE,'>','<',VNE,'+','-',VBEKI    * べき乗
  343.     .dc.w    '*','/',VAND,'&',VOR,'|','^','~','\','=','!'
  344. * 以下関数
  345.     .dc.w    __FABS,__FCEIL,__FFIX,__FFLOOR,__FFRAC
  346.     .dc.w    __FSGN,__FEXP,__FSQR,__FNPI,__FLOG10
  347.     .dc.w    __FLOG2,__FLOG,__FSIN,__FCOS,__FTAN
  348.     .dc.w    __FATANH,__FASIN,__FACOS,__FATAN,__FSINH
  349.     .dc.w    __FCOSH,__FTANH
  350. *
  351.     .dc.w    0        * NULL = End of Table
  352.  
  353. *---------------------------------------------
  354. * 演算子優先順位
  355. *---------------------------------------------
  356.  
  357. Lvs_1:
  358.     .dc.w    '=',0                * 代入
  359.     .dc.w    VAND,VOR            * 論理演算
  360.     .dc.w    '&','|','^',0            * ビット演算(実数では不可)
  361.     .dc.w    VEQU,VNE,'>','<',VGE,VLE,0    * 比較
  362.     .dc.w    VRROT,VLROT,VRSHIFT,VLSHIFT,0    * ローテート、シフト(実数では不可)
  363.     .dc.w    '+','-',0            * 加減
  364.     .dc.w    '*','/','\',VBEKI,0        * 乗除剰余、べき乗(整数では不可)
  365.     .dc.w    VDEC,VINC,VMINUS,'~','!',0    * 単項演算子('~'のみ実数では不可)
  366.     .dc.w    $ffff                * end of table
  367.  
  368. ******************************************************************************
  369. * サブルーチン
  370. ******************************************************************************
  371. * 前に_のない関数は最適化済み
  372.  
  373. BREAKON:
  374. * d0のみ破壊
  375.     move.w    brksts(pc),-(sp)    * BREAK mode
  376.     bra    @f
  377.  
  378. BREAKOFF:
  379. * d0のみ破壊
  380.     move.w    #-1,-(sp)        * read BREAK mode
  381.     DOS    _BREAKCK
  382.     addq.w    #2,sp
  383.     move.w    d0,brksts
  384.     *
  385.     clr.w    -(sp)            * BREAK Cut
  386. @@:    DOS    _BREAKCK
  387.     addq.w    #2,sp
  388.     rts
  389.  
  390. *---------------------------------------------
  391.  
  392. ctol:
  393. * long ctol(adrs)
  394. * d0,a0破壊
  395.     move.l    4(sp),d0
  396.     move.l    d0,a0
  397.     btst.l    #0,d0
  398.     bne    1f
  399.     * 偶数アドレス = 直接読み出来る
  400.     move.l    (a0),d0
  401.     rts
  402.  
  403. 1:    * 奇数アドレス = 直接読み出来ない
  404.     move.l    1(a0),d0    * 次のアドレスからH.L/L.H/L.L/DUMMYを読み取る
  405.     move.b    (a0),d0
  406.     ror.l    #8,d0
  407.     rts
  408.  
  409. *---------------------------------------------
  410.  
  411. check_kanji1:
  412. * 漢字1バイト目判定
  413.     move.l    4(sp),d1
  414. kcheck1:
  415.     moveq.l    #0,d0
  416.     cmp.l    #256,d1
  417.     bge    nonkanji    * 256以上は非漢字扱い
  418.     cmp.l    #$80-1,d1    * 0x00~0x7fは漢字1バイト目でない
  419.     bls    nonkanji
  420.     cmp.l    #$a0-1,d1    * 0x80~0x9fは漢字1バイト目
  421.     bls    kanji
  422.     cmp.l    #$e0-1,d1    * 0xa0~0xdfは漢字1バイト目でない
  423.     bls    nonkanji    * 本当は0xfe,0xffは漢字1バイト目ではない
  424. kanji:
  425.     moveq.l    #1,d0
  426. nonkanji:
  427.     tst.l    d0        * 漢字かどうかの判定をフラグに反映しておく
  428.     rts
  429.  
  430. *---------------------------------------------
  431.  
  432. isalnum:
  433. * 数字・アルファベット判定
  434.     move.b    4+3(sp),d1
  435. isalnum2:    * d1.b=code
  436.     moveq.l    #1,d0            * for True
  437.     cmp.b    #'0',d1
  438.     bcs    1f            * <'0'  : False
  439.     cmp.b    #'9',d1
  440.     bls    2f            * <='9' : True
  441.     cmp.b    #'A',d1
  442.     bcs    1f            * <'A'  : False
  443.     cmp.b    #'Z',d1
  444.     bls    2f            * <='Z' : True
  445.     cmp.b    #'a',d1
  446.     bcs    1f            * <'a'  : False
  447.     cmp.b    #'z',d1
  448.     bls    2f            * <='z' : True
  449. 1:    moveq.l    #0,d0            * False
  450. 2:    rts
  451.  
  452. *---------------------------------------------
  453.  
  454. __FNEG2    macro    dx
  455. local    L1
  456. * 符号反転
  457.     tst.l    dx
  458.     beq    L1
  459.     bchg.l    #31,dx
  460. L1:
  461.     .endm
  462.  
  463. ******************************************************************************
  464.  
  465. hash:    * ハッシュ計算
  466. * unsint hash(unchar *str)
  467. * d0,d2,a0破壊
  468.     move.l    4(sp),a0    * str
  469.     moveq.l    #0,d0        * h=0
  470.     moveq.l    #0,d2        * c (for .b = .w)
  471. @@:    move.b    (a0)+,d2
  472.     beq    @f        * EOS
  473.     mulu.w    #7,d0        * d0.l=d0.w*7
  474.     add.w    d2,d0
  475.     bra    @b
  476. *
  477. @@:    moveq.l    #0,d2        * for .l = .w
  478.     move.w    d0,d2        * 
  479.     rts
  480.  
  481. *---------------------------------------------
  482.  
  483. make_base:
  484. * 2/8/10/16進数文字列作成(整数のみ)
  485. * 一番長くなるのは2進数で32ビット分=32バイト+符号
  486. * base >0 : 正で処理 , base < 0 : 符号つきで処理
  487. * int make_base(int code,unchar dec[2+BINT+1],int base)
  488. ofs    =    (4*2)
  489. regs    .reg    d3/d4
  490.     movem.l    regs,-(sp)
  491.     move.l    ofs+4(sp),d0    * num(unsigned)<-code
  492.     moveq.l    #32+2,d3    * i
  493.     moveq.l    #0,d2        * sign=0(.wでいい)
  494.     move.l    ofs+12(sp),d1    * base<0?
  495.     bpl    1f        * No
  496.     * base<0 : 符号付き
  497.     tst.l    d0        * code<0?
  498.     bpl    2f        * No
  499.     * code<0
  500.     neg.l    d0        * num=-code
  501.     beq    2f        * num==0? Yes
  502.     * num!=0
  503.     moveq.l    #1,d2        * sign=1
  504. 2:    neg.l    d1        * base=-base
  505.     *
  506. 1:    move.l    ofs+8(sp),a0    * dec
  507.     lea    (a0,d3.l),a0    * dec[i]
  508.     clr.b    (a0)        *       =EOS
  509.     lea    b(pc),a1    * b[]
  510. 3:    cmp.l    d1,d0        * num>=base?
  511.     bcs    4f        * No
  512.     move.l    d0,d4
  513.     FPACK    __UMOD        * d4.l=num%base    d0%=d1(符号なし)
  514.     exg    d0,d4
  515.     move.b    (a1,d4.l),-(a0)    * dec[--i]=b[num%base];
  516.     subq.l    #1,d3        * --i
  517.     FPACK    __UDIV        * num/=base    d0/=d1(符号なし)
  518.     bra    3b
  519.     *
  520. 4:    move.b    (a1,d0.l),-(a0)    * dec[--i]=b[num]
  521.     subq.l    #1,d3        * --i
  522.     tst.w    d2        * sign==1?
  523.     beq    @f        * No
  524.     move.b    #'-',-(a0)    * 負号
  525.     subq.l    #1,d3        * --i
  526. @@:    move.l    d3,d0        * return(i)
  527.     movem.l    (sp)+,regs
  528.     rts
  529. *
  530. b    .dc.b    '0123456789ABCDEF',0    * atoi3bでも使う
  531.     .even
  532.  
  533. *---------------------------------------------
  534.  
  535. atoi3b:
  536. * int atoi3b(unchar *str,long *num,int base,unchar *(*after))
  537. *        4        8    12    16
  538. * base進数の文字列を数値に直す(実数対応):base=2~10,16
  539.     move.l    12(sp),d0    * base
  540.     cmp.l    #10,d0        * 10進数?
  541.     bne    @f        * No : とりあえず読み取りはatoi3bに任せる
  542.     * 10進数
  543.     tst.b    ffloat
  544.     beq    @f        * 整数
  545.     * 実数10進数読み取り
  546.     movem.l    4(sp),a0/a1    * str/*num
  547.     FPACK    __STOF        * -> d0.l
  548.     move.l    d0,(a1)        * -> *num
  549.     move.l    16(sp),a1
  550.     move.l    a0,(a1)        * *after=str
  551.     moveq.l    #0,d0        * ret
  552.     rts
  553. *
  554. ofs    =    (4*3)
  555. regs    .reg    d3-d5
  556. @@:    movem.l    regs,-(sp)
  557.     moveq.l    #0,d0        * v=0
  558.     moveq.l    #0,d5        * ret=0
  559.     lea    b(pc),a1    * 0~9,A~F
  560.     *
  561.     move.l    ofs+12(sp),d1    * base
  562.     move.l    ofs+4(sp),a0    * str
  563. 1:    move.b    (a0)+,d2    * c=*str++
  564.     beq    2f        * EOS
  565.     cmp.b    #'_',d2        * セパレーター
  566.     beq    1b        * 飛ばす
  567.     * 数字変換
  568.     cmp.b    #'a',d2
  569.     bcs    @f        * <'a'
  570.     and.b    #%1101_1111,d2    * 大文字化
  571. @@:    moveq.l    #-1,d3        * 数字
  572. @@:    addq.l    #1,d3
  573.     move.b    (a1,d3.l),d4    * b[数字]
  574.     beq    atoi3_err    * 数字文字列でない
  575.     cmp.b    d4,d2
  576.     bne    @b
  577.     cmp.l    d1,d3        * 数字>=base?
  578.     bcc    atoi3_err    * Yes : base範囲でない
  579.     FPACK    __LMUL        * v*=base    d0*=d1
  580.     add.l    d3,d0        * v+=数字
  581.     bra    1b
  582.     *
  583. atoi3_err:
  584.     moveq.l    #-2,d5        * エラー
  585. 2:    tst.b    ffloat
  586.     beq    @f        * 整数
  587.     * 整数->実数変換
  588.     FPACK    __LTOF        * signed int → float ;    d0 = d0
  589. @@:    move.l    ofs+8(sp),a1    * *num
  590.     move.l    d0,(a1)        * *num=v
  591.     move.l    ofs+16(sp),d4    * *after
  592.     beq    @f        * NULL
  593.     move.l    d4,a1
  594.     subq.l    #1,a0        * str-1
  595.     move.l    a0,(a1)        * *after=str-1
  596. @@:    move.l    d5,d0        * ret
  597.     movem.l    (sp)+,regs
  598.     rts
  599.  
  600. *---------------------------------------------
  601.  
  602. read_var_name:
  603. * 変数名読みだし
  604. * unchar *read_var_name(unchar *str,unchar vname[],int max)
  605. *                4    8        12
  606.     movem.l    4(sp),a0/a1/a2    * str/vname/max
  607.     moveq.l    #0,d2        * p=0
  608.     *
  609. 2:    move.b    (a0)+,d1    * c=*str++
  610.     beq    1f        * EOS
  611.     cmp.l    a2,d2        * p>=max?
  612.     bcs    @f        * NO
  613.     * over
  614.     moveq.l    #0,d0        * return(NULL)
  615.     rts
  616.     *
  617. @@:    * 変数に使えない文字が出てきたら終わり
  618.     cmp.b    #'_',d1
  619.     beq    @f        * '_'は大丈夫
  620.     bsr    isalnum2    * d1.b -> d0.l
  621.     tst.l    d0
  622.     beq    1f        * アルファベット+数字でない
  623.     or.b    #$20,d1        * 小文字化(ここに来るのは英数字のみなのでこれで良い)
  624. @@:    move.b    d1,(a1)+    * vname[p]=c
  625.     addq.l    #1,d2        * p++
  626.     bra    2b
  627.     *
  628. 1:    subq.l    #1,a0        * 使えない文字のところに合わせる
  629.     clr.b    (a1)        * vname[p]=0
  630.     * 変数名直後のアドレスを返す
  631.     move.l    a0,d0        * str
  632.     rts
  633.  
  634. *---------------------------------------------
  635.  
  636. var_num_write:
  637. * 変数に数値を書き込む
  638. * long var_num_write(long point,long num,int mode)
  639. *            4        8        12
  640.     movem.l    4(sp),d0/d1/d2    * point/num/mode
  641.     cmp.l    #VTOP,d0
  642.     bcs    @f        * point<VTOP
  643.     lea    var(pc),a1
  644.     cmp.l    vwsize(a1),d0    * point>var.vwsize?
  645.     bls    1f        * no
  646. @@:    * ポイントがおかしい
  647.     moveq.l    #-2,d0
  648.     rts
  649.     *
  650. 1:    move.l    vwork(a1),a0    * vwork
  651.     lea    (a0,d0.l),a0    * &vwork[point]
  652.     *
  653.     btst.l    #15,d2        * 強制再定義モード?
  654.     bne    @f        * Yes -> 再代入不可にかかわらず代入する
  655.     *
  656.     btst.b    #BVDAI,Vmd(a0)    * vwork[point+1]&VDAI?
  657.     beq    @f        * No
  658.     * 再代入不可
  659.     moveq.l    #-1,d0
  660.     rts
  661. *
  662. @@:    move.b    d2,Vmd(a0)    * vwork[point+1]=mode
  663.     * *(long *)vwork[point+2]=num
  664.     lea    Vnum(a0),a1
  665.     move.l    a1,d2
  666.     btst.l    #0,d2
  667.     bne    @f
  668.     * 偶数アドレス = 直接書き込める
  669.     move.l    d1,(a1)
  670.     bra    2f
  671. *
  672. @@:    * 奇数アドレス ; 68020以降なら一発書き込みなんだけど
  673.     move.b    d1,3(a1)    * L.L
  674.     lsr.l    #8,d1
  675.     move.w    d1,1(a1)    * H.L/L.H
  676.     swap    d1
  677.     move.b    d1,(a1)        * H.H
  678.     *
  679. 2:    moveq.l    #0,d1        * for .b=.l
  680.     move.b    (a0),d1        * vwork[point]
  681.     add.l    d1,d0        * +point
  682.     addq.l    #7,d0        * +6+1
  683.     rts
  684.  
  685. *---------------------------------------------
  686.  
  687. var_num_read:
  688. * 変数数値・モード読みだし
  689. * int var_num_read(long point,long *num)
  690. *            4    8
  691.     movem.l    4(sp),d0/a2    * point/*num
  692.     cmp.l    #VTOP,d0
  693.     bcs    @f        * point<VTOP
  694.     lea    var(pc),a1
  695.     cmp.l    vwsize(a1),d0    * point>var.vwsize?
  696.     bls    1f        * no
  697. @@:    * ポイントがおかしい
  698.     moveq.l    #VARAROVER,d0
  699.     rts
  700.     *
  701. 1:    move.l    vwork(a1),a0    * vwork
  702.     lea    (a0,d0.l),a0    * &vwork[point]
  703.     move.b    Vmd(a0),d0    * md=vwork[point+1]
  704.     move.b    d0,d1        * md
  705.     and.b    #VKAKU,d0
  706.     beq    @f
  707.     * 未確定
  708.     moveq.l    #VARNKAKU,d0
  709.     rts
  710.     *
  711. @@:    * 読みだし
  712.     pea    Vnum(a0)    * &vwork[point+2]
  713.     bsr    ctol        * -> d0.l(d0,a0破壊)
  714.     addq.l    #4,sp
  715.     * 変数交互変換
  716.     and.b    #VTYPE,d1    * 型取りだし
  717.     tst.b    ffloat
  718.     beq    @f        * 整数モード
  719.     * 実数モードにいる
  720.     tst.b    d1
  721.     bne    1f        * 実数変数である=そのまま
  722.     * 整数変数を実数で読み取る
  723.     FPACK    __LTOF        * signed int → float ;    d0 = d0
  724.     bra    1f
  725. *
  726. @@:    * 整数モード
  727.     tst.b    d1
  728.     beq    1f        * 整数変数である=そのまま
  729.     * 実数変数を整数で読み取る
  730.     FPACK    __FTOL        * float → signed int ; d0 = d0
  731.     bcc    1f
  732.     * 整数化出来ない
  733.     moveq.l    #VARCCINT,d0
  734.     rts
  735.     *
  736. 1:    move.l    d0,(a2)        * -> *num
  737.     moveq.l    #0,d0        * return(0)
  738.     rts
  739.  
  740. *---------------------------------------------
  741.  
  742. var_search:
  743. * long var_search(unchar *vname)
  744. * 変数サーチ
  745. * return=0:その変数は定義されていない
  746. *     >0:その変数の格納位置(数値確定)
  747. *     <0:その変数の格納位置*-1(数値未確定)
  748. ofs=    (4*3)
  749. regs    .reg    d3/d6/a3
  750.     movem.l    regs,-(sp)
  751.     lea    var(pc),a1
  752.     cmp.l    #VTOP,vpoint(a1)    * vpoint==VTOP?
  753.     beq    vsNone        * Yes : 変数が1つもない
  754.     *
  755.     * ハッシュで最初のサーチポイントを決める
  756.     * p=vhash[hash(vname)%vhsize];
  757.     move.l    4+ofs(sp),a3    * vname
  758.     pea    (a3)
  759.     bsr    hash        * a0,d0,d2破壊 -> d0.l=d0.w
  760.     addq.l    #4,sp
  761.     *
  762.     lea    var(pc),a1
  763.     divu.w    vhsize(a1),d0    * d0.l.w=d0.l/vhsize.w ... d0.h.w
  764.     clr.w    d0        * for .w = .l ; 答部分を消す
  765.     swap    d0        * 余り(=d0.l)
  766.     add.l    d0,d0
  767.     add.l    d0,d0        * *4 for long
  768.     move.l    vhash(a1),a0    * vhash
  769.     move.l    (a0,d0.l),d6    * p=vhash[...]
  770.     *
  771.     bclr.l    #31,d6        * p&BIT31?
  772.     sne.b    d3        * Yes -> fdbl=1/BIT31=0
  773.     moveq.l    #1,d0
  774.     and.l    d0,d3        * fdbl=0/1
  775.     tst.l    d6
  776.     bls    vsNone        * p<=0
  777.     * p>0 ; ハッシュにはあった
  778.     * len=strlen(vname) ; 変数名長
  779.     moveq.l    #-1,d2        * len=-1
  780. @@:    addq.w    #1,d2        * len++
  781.     tst.b    (a3)+
  782.     bne    @b
  783.     *
  784.     move.l    vwork(a1),a3    * vwork
  785.     move.l    vpoint(a1),d0    * vpoint
  786.     lea    (a3,d0.l),a2    * &vwork[vpoint]
  787.     add.l    d6,a3        * &vwork[p]
  788.     * d3.w=fdbl,d1.w=vlen,d2.w=len,d6.l=p,a1=var,a3=vname/&vwork[p],a2=&vwork[vpoint]
  789. vsloop:    * 格納エリアからサーチ
  790.     * 比較
  791.     moveq.l    #0,d1        * for .b = .w = .l
  792.     move.b    (a3),d1        * vlen=var.vwork[p]
  793.     cmp.w    d1,d2        * vlen==len? 変数名長も一致?
  794.     bne    4f        * No
  795.     * 変数名比較
  796.     lea    Vname(a3),a0    * vwork[p+6]
  797.     move.l    4+ofs(sp),a1    * vname
  798.     move.w    d1,d0        * vlen
  799.     subq.w    #1,d0        * -1 for dbra
  800. @@:    cmp.b    (a0)+,(a1)+    * vwork <-> vname
  801.     dbne    d0,@b
  802.     bne    4f        * 不一致で終わった時
  803.     * 一致で終わった
  804.     move.l    d6,d0        * p
  805.     move.b    Vmd(a3),d1    * m=vwork[p+1] ; モード・型
  806.     and.b    #VKAKU,d1    * m&VKAKU
  807.     beq    vsRet        * p : 確定
  808.     neg.l    d0        * -p: 未確定
  809.     bra    vsRet        * return(m&VKAKU? -p:p) ; 未確定:確定
  810.     *
  811. 4:    * 変数名長が一致しない時は即不一致
  812.     tst.w    d3        * fdbl?
  813.     beq    vsNone        * Yes : ハッシュ重複無し:ここで一致しなければ無し
  814.     * 次の変数へ
  815.     add.l    d1,d6        * p+vlen
  816.     addq.l    #sizeV+1,d6    * p+(6+1)
  817.     lea    sizeV+1(a3,d1.l),a3    * &vwork[p]
  818.     cmp.l    a2,a3        * &vwork[p]<&vwork[vpoint]?
  819.     bcs    vsloop        * Yes
  820. vsNone:    * ハッシュにない/この変数は登録されていない/変数が全く無い
  821.     moveq.l    #0,d0
  822. vsRet:    movem.l    (sp)+,regs
  823.     rts
  824.  
  825. *---------------------------------------------
  826.  
  827. var_hash_set:
  828. * ハッシュ登録
  829. * int var_hash_set(unchar *vname)
  830.     move.l    4(sp),-(sp)
  831.     bsr    hash        * h=d0.l(=.w)
  832.     addq.l    #4,sp
  833.     *
  834.     lea    var(pc),a0
  835.     divu.w    vhsize(a0),d0    * hash%var.vhsize ; d1.h.w=余り
  836.     clr.w    d0        * for .w = .l
  837.     swap    d0        * h=d0.l.w=d0.l
  838.     add.l    d0,d0
  839.     add.l    d0,d0        * *4
  840.     move.l    vhash(a0),a1    * vhash
  841.     lea    (a1,d0.l),a1    * vhash[h]
  842.     tst.l    (a1)        * すでにそのハッシュは使われている?
  843.     beq    @f        * No
  844.     * 使われている
  845. *    bset.l    #31,(a1)    * |BIT31 = 重複フラグ
  846.     bset.b    #7,(a1)        * 上と同意になる
  847.     moveq.l    #1,d0        * return(1)
  848.     rts
  849. *
  850. @@:    move.l    vpoint(a0),(a1)    * var.vhash[h]=var.vpoint
  851.     moveq.l    #0,d0        * return(0)
  852.     rts            * 登録完了
  853.  
  854. *---------------------------------------------
  855.  
  856. var_define:
  857. * long var_define(unchar *vname,int mode)
  858. * 変数登録(仮確定)
  859. * mode : VDAI=0:普通/1:再代入不可 , VTYPEも指定可能
  860. ofs    =    (4*4)
  861. regs    .reg    d3-d5/a3
  862.     movem.l    regs,-(sp)
  863.     * d3.l=p,d4.l=p0,d5.w=len,a3=vname
  864.     move.l    4+ofs(sp),a3    * vname
  865.     pea    (a3)
  866.     bsr    var_search    * 新規登録/変更判定
  867.     addq.l    #4,sp
  868.     tst.l    d0
  869.     beq    @f
  870.     * p!=0 : 2重定義
  871.     moveq.l    #-2,d0
  872.     bra    vdRet
  873. *
  874. @@:    * len=strlen(vname) ; 変数名長
  875.     move.l    a3,a0
  876.     moveq.l    #-1,d5        * len=-1
  877. @@:    addq.l    #1,d5        * len++
  878.     tst.b    (a0)+
  879.     bne    @b        * .b=.w=.l
  880.     cmp.w    vlmax(a1),d5    * len>vlmax?
  881.     bls    @f        * No(<=)
  882.     * Yes : 変数名長が長すぎる
  883.     moveq.l    #-3,d0
  884.     bra    vdRet
  885. *
  886. @@:    * 変数は未定義 -> 新規登録:最初は必ず数値未確定
  887.     lea    var(pc),a1
  888.     move.l    vpoint(a1),d3    * p =vpoint
  889.     move.l    d3,d4        * p0=vpoint
  890.     move.l    d3,d0        * p
  891.     addq.l    #sizeV+1,d0    * 1+1+LLONG+1
  892.     add.l    d5,d0
  893.     cmp.l    vwsize(a1),d0    * p+1+1+LLONG+len+1>=vwsize?
  894.     bcs    @f        * No(<)
  895.     * これ以上格納できない
  896.     moveq.l    #-1,d0
  897.     bra    vdRet
  898. *
  899. @@:    * ハッシュ設定
  900.     pea    (a3)        * vname
  901.     bsr    var_hash_set
  902.     addq.l    #4,sp
  903.     *
  904.     * 変数格納
  905.     lea    var(pc),a1
  906.     move.l    vwork(a1),a2    * vwork
  907.     add.l    d3,a2        * &vwork[p]
  908.     *
  909.     move.b    d5,(a2)+    * vwork[p++]=(unchar)len ; 変数名長
  910.     move.b    3+8+ofs(sp),(a2)+    * vwork[p++]=(unchar)mode ; TYPE
  911.     * 0/0.0で仮確定
  912.     * 4バイトにデータを書き込むが、奇数バイト境界もあるので1バイトごと書いている
  913.     clr.b    (a2)+        * 整数も実数も0は0
  914.     clr.b    (a2)+
  915.     clr.b    (a2)+
  916.     clr.b    (a2)+        * vwork[p+=LLONG]=0/0.0
  917. @@:    move.b    (a3)+,(a2)+    * strcpy(&vwork[p],vname) ; 変数名格納
  918.     bne    @b
  919.     addq.l    #sizeV+1,d3    * p+1+1+LLONG+1
  920.     add.l    d5,d3        *  +len
  921.     move.l    d3,vpoint(a1)    * vpoint=次の書きこみ位置
  922.     * 変数個数
  923.     addq.l    #1,vlots(a1)    * vlots++;
  924.     move.l    d4,d0        * return(p0) ; この変数の先頭アドレスを返す
  925. vdRet:    movem.l    (sp)+,regs
  926.     rts
  927.  
  928. *---------------------------------------------
  929.  
  930. var_read2:
  931. * 変数読みだし
  932. * int var_read2(unchar *vname,long *num,long *pp)
  933. *            4    8    12
  934. * return : 0=読み出せた , VARNKAKU/VARNDEF/VARAROVER/VARCCINT=エラー
  935.     move.l    4(sp),-(sp)
  936.     bsr    var_search    * p
  937.     addq.l    #4,sp
  938.     tst.l    d0        * p=0?
  939.     bne    @f        * NO
  940.     * 変数は未定義(p=0)
  941.     moveq.l    #VARNDEF,d0
  942.     rts
  943. *
  944. @@:    move.l    12(sp),a0
  945.     move.l    d0,(a0)        * *pp=p
  946.     bge    @f        * >=0
  947.     * 変数が未確定(p<0)
  948.     moveq.l    #VARNKAKU,d0
  949.     rts
  950. *
  951. @@:    * 読みだし
  952.     move.l    8(sp),-(sp)    * num
  953.     move.l    d0,-(sp)    * p
  954.     bsr    var_num_read
  955.     addq.l    #8,sp
  956.     rts
  957.  
  958. *---------------------------------------------
  959.  
  960. _NumVarRead:
  961.     link a6,#0
  962.     movem.l d3/d4/d5/d6/a3/a4/a5,-(sp)
  963.     move.l 12(a6),a5
  964.     move.l 16(a6),a4
  965.     move.l 20(a6),a3
  966.     moveq.l #10,d1
  967.     moveq.l #0,d5
  968.     moveq.l #22,d2
  969.     add.l #var,d2
  970.     move.l d2,a0
  971.     move.l d5,d0
  972.     move.w (a0),d0
  973.     addq.l #2,d0
  974.     moveq.l #-2,d2
  975.     and.l d2,d0
  976.     sub.l d0,sp
  977.     move.l sp,d4
  978.     jbne N124
  979.     moveq.l #55,d2
  980.     move.l d2,(a3)
  981.     move.l d5,d0
  982.     jbra N123
  983. N124:
  984.     moveq.l #0,d2
  985.     move.l d2,(a4)
  986.     move.l 8(a6),d6
  987.     move.l d2,(a3)
  988.     move.l 8(a6),a0
  989.     cmp.b #45,(a0)
  990.     jbne N125
  991.     moveq.l #1,d5
  992.     addq.w #1,a0
  993.     move.l a0,8(a6)
  994. N125:
  995.     move.l 8(a6),a0
  996.     moveq.l #0,d0
  997.     move.b (a0),d0
  998.     moveq.l #-36,d2
  999.     add.l d2,d0
  1000.     moveq.l #28,d2
  1001.     cmp.l d2,d0
  1002.     jbhi N126
  1003.     add.l d0,d0
  1004. NI133:
  1005.     move.w N133-NI133-2(pc,d0.l),d2
  1006.     jmp 2(pc,d2.w)
  1007. N133:
  1008.     .dc.w N132-N133
  1009.     .dc.w N130-N133
  1010.     .dc.w N126-N133
  1011.     .dc.w N127-N133
  1012.     .dc.w N126-N133
  1013.     .dc.w N126-N133
  1014.     .dc.w N126-N133
  1015.     .dc.w N126-N133
  1016.     .dc.w N126-N133
  1017.     .dc.w N126-N133
  1018.     .dc.w N126-N133
  1019.     .dc.w N126-N133
  1020.     .dc.w N126-N133
  1021.     .dc.w N126-N133
  1022.     .dc.w N126-N133
  1023.     .dc.w N126-N133
  1024.     .dc.w N126-N133
  1025.     .dc.w N126-N133
  1026.     .dc.w N126-N133
  1027.     .dc.w N126-N133
  1028.     .dc.w N126-N133
  1029.     .dc.w N126-N133
  1030.     .dc.w N126-N133
  1031.     .dc.w N126-N133
  1032.     .dc.w N126-N133
  1033.     .dc.w N126-N133
  1034.     .dc.w N126-N133
  1035.     .dc.w N126-N133
  1036.     .dc.w N131-N133
  1037. N127:
  1038.     move.l 8(a6),a0
  1039.     addq.w #1,a0
  1040.     move.l a0,8(a6)
  1041.     clr.w d3
  1042.     move.b (a0)+,d3
  1043.     move.l a0,8(a6)
  1044.     moveq.l #0,d0
  1045.     move.w d3,d0
  1046.     move.l d0,-(sp)
  1047.     jbsr check_kanji1
  1048.     tst.l d0
  1049.     jbeq N128
  1050.     move.w d3,d0
  1051.     lsl.w #8,d0
  1052.     move.l 8(a6),a0
  1053.     clr.w d1
  1054.     move.b (a0)+,d1
  1055.     move.w d0,d3
  1056.     or.w d1,d3
  1057.     move.l a0,8(a6)
  1058. N128:
  1059.     move.l 8(a6),a0
  1060.     move.b (a0)+,d0
  1061.     move.l a0,8(a6)
  1062.     cmp.b #39,d0
  1063.     jbeq N129
  1064.     moveq.l #14,d2
  1065.     jbra N152
  1066. N129:
  1067.     moveq.l #0,d0
  1068.     move.w d3,d0
  1069.     move.l d0,(a5)
  1070.     jbra N151
  1071. N130:
  1072.     moveq.l #2,d1
  1073.     jbra N126
  1074. N131:
  1075.     moveq.l #8,d1
  1076.     jbra N126
  1077. N132:
  1078.     moveq.l #16,d1
  1079. N126:
  1080.     moveq.l #10,d2
  1081.     cmp.l d1,d2
  1082.     jbne N135
  1083.     move.l 8(a6),a0
  1084.     clr.w d3
  1085.     move.b (a0),d3
  1086.     cmp.w #47,d3
  1087.     jbls N137
  1088.     cmp.w #57,d3
  1089.     jbls N149
  1090. N137:
  1091.     moveq.l #0,d0
  1092.     move.w d3,d0
  1093.     move.l d0,-(sp)
  1094.     jbsr isalnum
  1095.     addq.w #4,sp
  1096.     tst.l d0
  1097.     jbne N138
  1098.     cmp.w #95,d3
  1099.     jbeq N138
  1100.     moveq.l #58,d2
  1101.     jbra N152
  1102. N138:
  1103.     moveq.l #22,d2
  1104.     add.l #var,d2
  1105.     move.l d2,a0
  1106.     moveq.l #0,d0
  1107.     move.w (a0),d0
  1108.     move.l d0,-(sp)
  1109.     move.l d4,-(sp)
  1110.     move.l 8(a6),-(sp)
  1111.     jbsr read_var_name
  1112.     move.l d0,8(a6)
  1113.     lea 12(sp),sp
  1114.     jbne N139
  1115.     moveq.l #53,d2
  1116.     jbra N152
  1117. N139:
  1118.     move.l a4,-(sp)
  1119.     move.l a5,-(sp)
  1120.     move.l d4,-(sp)
  1121.     jbsr var_read2
  1122.     move.l d0,d3
  1123.     lea 12(sp),sp
  1124.     moveq.l #50,d2
  1125.     cmp.l d3,d2
  1126.     jbne N140
  1127.     tst.b    ftei
  1128.     beq    @f
  1129.     pea    (0|VDAI).w    * 定数モード
  1130.     bra    1f
  1131. @@:    pea    0.w        * 普通モード
  1132. 1:    move.l d4,-(sp)
  1133.     jbsr var_define
  1134.     move.l d0,(a4)
  1135.     jbge N141
  1136.     moveq.l #-2,d2
  1137.     cmp.l d0,d2
  1138.     jbeq N144
  1139.     moveq.l #-1,d2
  1140.     cmp.l d0,d2
  1141.     jbne N155
  1142.     moveq.l #54,d2
  1143.     jbra N153
  1144. N144:
  1145.     moveq.l #57,d2
  1146. N153:
  1147.     move.l d2,(a3)
  1148.     jbra N155
  1149. N141:
  1150.     neg.l (a4)
  1151.     bra    N148
  1152. N140:
  1153.     tst.l d3
  1154.     jbeq N148
  1155.     move.l d3,(a3)
  1156. N155:
  1157.     moveq.l #0,d0
  1158.     jbra N123
  1159. N135:
  1160.     addq.l #1,8(a6)
  1161.     addq.l #1,d6
  1162. N149:
  1163.     pea 8(a6)
  1164.     move.l d1,-(sp)
  1165.     move.l a5,-(sp)
  1166.     move.l 8(a6),-(sp)
  1167.     jbsr atoi3b
  1168. N148:
  1169.     cmp.l 8(a6),d6
  1170.     jbne N150
  1171.     moveq.l #1,d2
  1172. N152:
  1173.     move.l d2,(a3)
  1174.     jbra N155
  1175. N150:
  1176.     tst.l d5
  1177.     jbeq N151
  1178. *
  1179.     tst.b    ffloat
  1180.     beq    @f        * 整数
  1181.     * float符号反転
  1182.     move.l    (a5),d0
  1183.     __FNEG2    d0        * floatでは負号処理が変わる
  1184.     move.l    d0,(a5)
  1185.     bra    N151
  1186. *
  1187. @@:    * 整数符号反転
  1188.     neg.l (a5)
  1189. N151:
  1190.     move.l 8(a6),d0
  1191. N123:
  1192.     movem.l -28(a6),d3/d4/d5/d6/a3/a4/a5
  1193.     unlk a6
  1194.     rts
  1195.  
  1196. *---------------------------------------------
  1197. * 関数実行
  1198. * プログラムを書き替えるため、キャッシュクリアが必要
  1199.  
  1200. func:    .dc.w    FeMin        * ここが書き変わる
  1201.     rts
  1202.  
  1203. *---------------------------------------------
  1204.  
  1205. Enzan:
  1206. * int Enzan(void)
  1207. * 演算&符号処理(代入は外部のfuncで処理)
  1208. * スタック上の処理だけ
  1209. * return : d0.l : >0:演算子 , <0:エラー(d1.l=エラーコード)
  1210. * d1=v2,d2=v1,d3=e,d4=vs,a1=Vsikis,a2=Vsikis.vstack[vs],d0/d5/a0=汎用
  1211. ofs    = (4*3)
  1212. regs    .reg    d3-d5
  1213.     movem.l    regs,-(sp)
  1214.     lea    Vsikis(pc),a1
  1215.     move.w    vs(a1),d4    * vs
  1216.     beq    Eill        * vs==0 -> エラー(無いはずだけど)
  1217.     * 第2項取り出し
  1218.     * v2=vstack[--vs]
  1219.     subq.w    #1,d4        * --vs
  1220.     move.w    d4,vs(a1)    * 記録
  1221.     move.l    vstack(a1),a0    * vstack
  1222.     moveq.l    #0,d0        * for .w -> .l
  1223.     move.w    d4,d0
  1224.     add.l    d0,d0
  1225.     add.l    d0,d0        * *4 for long
  1226.     lea.l    (a0,d0.l),a2    * vstack[vs]
  1227.     move.l    (a2),d1        * v2
  1228.     * 演算子取り出し
  1229.     * e=Vsikis.estack[--Vsikis.es];
  1230.     move.l    estack(a1),a0    * estack
  1231.     moveq.l    #0,d0        * for .w -> .l
  1232.     move.w    es(a1),d0    * es
  1233.     subq.w    #1,d0        * --es
  1234.     move.w    d0,es(a1)    * 記録
  1235.     add.l    d0,d0        * *2 for unsint
  1236.     move.w    (a0,d0.l),d3    * e
  1237.     *
  1238.     * 単項演算子
  1239.     lea    E1tableI(pc),a0    * 整数
  1240.     tst.b    ffloat
  1241.     beq    @f
  1242.     cmp.w    #FeMin,d3
  1243.     bcc    Func        * >=FeMin;演算子である
  1244.     lea    E1tableF(pc),a0    * float
  1245. @@:    move.l    (a0)+,d5    * jump|code
  1246.     beq    kou2        * -> end of table
  1247.     cmp.w    d3,d5        * =code?
  1248.     bne    @b        * no
  1249.     swap    d5        * d5=jump
  1250.     move.l    d1,d0        * いろいろと使うので;d0=v2
  1251.     jsr    -4(a0,d5.w)    * 単項演算子であった
  1252. 70:    * <- ここに帰ってくる
  1253.     move.l    d1,(a2)        * vstack[vs]=v2
  1254.     addq.w    #1,d4        * vs++
  1255.     move.w    d4,vs(a1)    * 保存
  1256. Eok:    moveq.l    #0,d0        * for .w = .l
  1257.     move.w    d3,d0        * return(e)
  1258. Eret:    movem.l    (sp)+,regs
  1259.     rts
  1260. *
  1261. Eill:    * 式エラー(これはメインで起こる)
  1262.     moveq.l    #VSILL,d1
  1263.     moveq.l    #-1,d0
  1264.     bra    Eret
  1265. *
  1266. * 以下は各演算子で起こる
  1267. Eover2:    * オーバー/アンダー
  1268.     bvs    Eover        * V=0:アンダー,V=1:オーバー
  1269. Eunder:    * アンダーフロー
  1270.     moveq.l    #VSUNDER,d1
  1271.     bra    Eerr
  1272. *
  1273. Eover:    * オーバーフロー
  1274.     moveq.l    #VSOVER,d1
  1275. Eerr:    moveq.l    #-1,d0        * エラーの印
  1276.     add.l    #4,sp        * jsrの戻りアドレスを消す
  1277.     bra    Eret
  1278.  
  1279. Ediv2:    * オーバー/アンダー/0除算
  1280.     bne    Eover2        * Z=0:over/under,Z=1:0除算
  1281.     * Z=1:0除算
  1282. Ediv0:    * 0除算
  1283.     moveq.l    #VS0DIV,d1
  1284.     bra    Eerr
  1285. *
  1286. *
  1287. Func:    * 関数実行;関数は単項演算子である(float)
  1288.     * プログラム内部を書き替えるためキャッシュをoffしてから実行する
  1289.     * 自己書き替え
  1290.     move.w    d3,func        * eがfeファンクションコールそのものである
  1291.     * キャッシュクリア
  1292.     move.b    $e8e00b,d0    * bit7-4:CPU type
  1293.     cmp.b    #%1111_0000,d0
  1294.     bcc    @f        * =68000
  1295.     * 68020以降機
  1296.     movem.l    d1-d2,-(sp)
  1297.     moveq.l    #1,d1        * キャッシュ状態読み出し
  1298.     IOCS    _SYS_STAT
  1299.     move.l    d1,-(sp)    * 保存
  1300.     moveq.l    #0,d2        * キャッシュoff
  1301.     moveq.l    #4,d1        * キャッシュのセット(d2.l)
  1302.     IOCS    _SYS_STAT
  1303.     * キャッシュ戻し
  1304.     move.l    (sp)+,d2    * 前のキャッシュ状態
  1305.     moveq.l    #4,d1        * キャッシュのセット(d2.l)
  1306.     IOCS    _SYS_STAT    * キャッシュ状態を設定
  1307.     movem.l    (sp)+,d1-d2
  1308. @@:    *
  1309.     move.l    d1,d0        * v2
  1310.     bsr    func        * 関数実行($fexx);全て単項演算子 v2=func(v2)
  1311.     bcs    Eover3        * エラーチェック
  1312.     move.l    d0,d1        * v2
  1313.     bra    70b
  1314. *
  1315. Eover3:    * オーバー/アンダー/引数おかしい
  1316.     subq.l    #4,sp        * 後でadd.l #4,spがあるのでそれをスキップさせるため(フラグ不変)
  1317.     bvs    Eover2
  1318. *    bne    Eover2        * Z=0:over/under,Z=1:引数おかしい
  1319.     * 引数エラー
  1320.     moveq.l    #VSARG,d1
  1321.     bra    Eerr
  1322. *
  1323. * テーブルは良く出てくる順に並べる
  1324. E1tableI:    * 整数1項演算子テーブル
  1325.     .dc.w    EminusI-$,VMINUS    * 負号
  1326.     .dc.w    EbnotI-$,'~'        * ビットNOT
  1327.     .dc.w    EincI-$,VINC        * ++
  1328.     .dc.w    EdecI-$,VDEC        * --
  1329.     .dc.w    EnotI-$,'!'        * 論理NOT
  1330.     .dc.w    0,0
  1331. *
  1332. E1tableF:    * 実数1項演算子テーブル
  1333.     .dc.w    EminusF-$,VMINUS    * 負号
  1334.     .dc.w    EincF-$,VINC        * ++
  1335.     .dc.w    EdecF-$,VDEC        * --
  1336.     .dc.w    EnotF-$,'!'        * 論理NOT
  1337.     .dc.w    0,0
  1338. *
  1339. **** 整数
  1340. EminusI:
  1341.     neg.l    d1        * v2=-v2
  1342.     rts
  1343. EbnotI:
  1344.     not.l    d1        * v2=~v2
  1345.     rts
  1346. EincI:
  1347.     addq.l    #1,d1        * v2++(オーバーフローチェックなし)
  1348.     rts
  1349. EdecI:
  1350.     subq.l    #1,d1        * v2--(アンダーフローチェックなし)
  1351.     rts
  1352. EnotI:
  1353.     tst.l    d1
  1354.     seq    d1        * 0->1,!=0->0
  1355.     moveq.l    #1,d0
  1356.     and.l    d0,d1        * 0/1
  1357.     rts
  1358. *
  1359. **** 実数
  1360. EminusF:
  1361.     __FNEG2    d1        * 負号
  1362.     rts
  1363. EincF:
  1364.     FPACK    __FADDONE    * v2++
  1365.     bra    @f
  1366. EdecF:
  1367.     FPACK    __FSUBONE    * v2--
  1368. @@:    bcs    Eover2
  1369.     move.l    d0,d1
  1370.     rts
  1371. EnotF:
  1372.     FPACK    __FTST        * v1==0?
  1373.     seq    d0        * 0->1,!=0->0
  1374.     moveq.l    #1,d1
  1375.     and.l    d1,d0        * 0/1
  1376.     FPACK    __LTOF        * signed int → float ;    d0 = d0
  1377.     move.l    d0,d1
  1378.     rts
  1379. *
  1380. *
  1381. kou2:    * 2項演算子
  1382.     * if (Vsikis.vs==0) return(-1); /* error : 第1項がない */
  1383.     tst.w    d4        * vs==0?
  1384.     beq    Eill        * Yes
  1385.     * 第1項取り出し
  1386.     move.l    -4(a2),d2    * v1=vstack[vs-1]
  1387.     * 2項演算
  1388.     lea    E2tableI(pc),a0    * 整数
  1389.     tst.b    ffloat
  1390.     beq    @f
  1391.     * 実数
  1392.     lea    E2tableF(pc),a0    * 実数
  1393. @@:    move.l    (a0)+,d5    * jump|code
  1394.     beq    @f        * -> end of table
  1395.     cmp.w    d3,d5        * =code?
  1396.     bne    @b        * no
  1397.     swap    d5        * d5=jump
  1398.     move.l    d2,d0        * いろいろと使うので
  1399.     jsr    -4(a0,d5.w)
  1400. @@:    * <- ここに帰ってくる
  1401.     move.l    d2,-4(a2)    * vstack[vs-1]=v1
  1402.     bra    Eok
  1403. *
  1404. *
  1405. E2tableI:    * 整数2項演算子テーブル
  1406.     .dc.w    Edainyu2-$,'='
  1407.     .dc.w    Eplus2I-$,'+'
  1408.     .dc.w    Eminus2I-$,'-'
  1409.     .dc.w    Emul2I-$,'*'
  1410.     .dc.w    Ediv2I-$,'/'
  1411.     .dc.w    Emod2I-$,'\'
  1412.     .dc.w    Eband2I-$,'&'
  1413.     .dc.w    Ebor2I-$,'|'
  1414.     .dc.w    Ebxor2I-$,'^'
  1415.     .dc.w    Ershift2I-$,VRSHIFT
  1416.     .dc.w    Elshift2I-$,VLSHIFT
  1417.     .dc.w    Errot2I-$,VRROT
  1418.     .dc.w    Elrot2I-$,VLROT
  1419.     .dc.w    Eand2I-$,VAND
  1420.     .dc.w    Eor2I-$,VOR
  1421.     .dc.w    Egt2I-$,'>'
  1422.     .dc.w    Elt2I-$,'<'
  1423.     .dc.w    Eequ2I-$,VEQU
  1424.     .dc.w    Ene2I-$,VNE
  1425.     .dc.w    Ege2I-$,VGE
  1426.     .dc.w    Ele2I-$,VLE
  1427.     .dc.w    0,0
  1428. *
  1429. E2tableF:    * 実数2項演算子テーブル
  1430.     .dc.w    Edainyu2-$,'='
  1431.     .dc.w    Eplus2F-$,'+'
  1432.     .dc.w    Eminus2F-$,'-'
  1433.     .dc.w    Emul2F-$,'*'
  1434.     .dc.w    Ediv2F-$,'/'
  1435.     .dc.w    Emod2F-$,'\'
  1436.     .dc.w    Eand2F-$,VAND
  1437.     .dc.w    Eor2F-$,VOR
  1438.     .dc.w    Egt2F-$,'>'
  1439.     .dc.w    Elt2F-$,'<'
  1440.     .dc.w    Eequ2F-$,VEQU
  1441.     .dc.w    Ene2F-$,VNE
  1442.     .dc.w    Ege2F-$,VGE
  1443.     .dc.w    Ele2F-$,VLE
  1444.     .dc.w    Epower2F-$,VBEKI
  1445.     .dc.w    0,0
  1446. *
  1447. **** 整数・実数両用
  1448. Edainyu2:
  1449.     movem.l    d1-d2,-(sp)
  1450.     move.l    d1,-(sp)    * v2
  1451.     bsr    Dainyu
  1452.     addq.l    #4,sp
  1453.     movem.l    (sp)+,d1-d2
  1454.     tst.l    d0
  1455.     bne    @f
  1456.     move.l    d1,d2        * v1=v2
  1457.     rts
  1458. @@:    * funcのエラー
  1459.     move.l    d0,d1        * Dainyuの返すエラーコード
  1460.     bra    Eerr
  1461. *
  1462. **** 整数
  1463. Eplus2I:
  1464.     add.l    d1,d2        *(オーバーフローチェックなし)
  1465.     rts
  1466. Eminus2I:
  1467.     sub.l    d1,d2        *(アンダーフローチェックなし)
  1468.     rts
  1469. Eband2I:
  1470.     and.l    d1,d2
  1471.     rts
  1472. Ebor2I:
  1473.     or.l    d1,d2
  1474.     rts
  1475. Ebxor2I:
  1476.     eor.l    d1,d2
  1477.     rts
  1478. Ershift2I:
  1479.     lsr.l    d1,d2
  1480.     rts
  1481. Elshift2I:
  1482.     lsl.l    d1,d2
  1483.     rts
  1484. Errot2I:
  1485.     ror.l    d1,d2
  1486.     rts
  1487. Elrot2I:
  1488.     rol.l    d1,d2
  1489.     rts
  1490. Egt2I:
  1491.     cmp.l    d1,d2
  1492.     sgt    d2
  1493.     bra    E0
  1494. Elt2I:
  1495.     cmp.l    d1,d2
  1496.     slt    d2
  1497.     bra    E0
  1498. Eequ2I:
  1499.     cmp.l    d1,d2
  1500.     seq    d2
  1501.     bra    E0
  1502. Ene2I:
  1503.     cmp.l    d1,d2
  1504.     sne    d2
  1505.     bra    E0
  1506. Ege2I:
  1507.     cmp.l    d1,d2
  1508.     sge    d2
  1509.     bra    E0
  1510. Ele2I:
  1511.     cmp.l    d1,d2
  1512.     sle    d2
  1513. E0:    moveq.l    #1,d0
  1514.     and.l    d0,d2
  1515.     rts
  1516. Eand2I:
  1517.     and.l    d1,d2
  1518.     sne    d2
  1519.     bra    E0
  1520. Eor2I:
  1521.     or.l    d1,d2
  1522.     sne    d2
  1523.     bra    E0
  1524. Emul2I:
  1525.     * 64bitで演算させ、下位32ビットを取る
  1526.     * このため、オーバーフローが出ない
  1527.     FPACK    __IMUL        * d0d1=v1(d0)*v2(d1)
  1528.     move.l    d1,d2        * v1=
  1529.     rts
  1530. Ediv2I:
  1531.     FPACK    __LDIV        * d0=v1(d0)/v2(d1)
  1532.     bcs    Ediv0        * C=1 ; 0除算
  1533.     move.l    d0,d2        * v1=
  1534.     rts
  1535. Emod2I:
  1536.     FPACK    __LMOD        * d0=v1(d0)%d1(d1)
  1537.     bcs    Ediv0        * C=1 ; 0除算
  1538.     move.l    d0,d2        * v1=
  1539.     rts
  1540. *
  1541. **** 実数
  1542. Eplus2F:
  1543.     FPACK    __FADD        * v2+v1(順序関係なし)
  1544.     bcs    Eover2
  1545.     move.l    d0,d2
  1546.     rts
  1547. Eminus2F:
  1548.     FPACK    __FADD        * v1-v2
  1549.     bcs    Eover2
  1550.     move.l    d0,d2
  1551.     rts
  1552. Emul2F:
  1553.     FPACK    __FMUL        * d0=d0*d1(順序関係なし)
  1554.     bcs    Eover2
  1555.     move.l    d0,d2
  1556.     rts
  1557. Ediv2F:
  1558.     FPACK    __FDIV        * d0=d0/d1
  1559.     bcs    Ediv2        * C=1 ; 0除算
  1560.     move.l    d0,d2
  1561.     rts
  1562. Emod2F:
  1563.     FPACK    __FMOD        * d0=d0%d1
  1564.     bcs    Ediv2        * C=1 ; 0除算
  1565.     move.l    d0,d2
  1566.     rts
  1567. Epower2F:
  1568.     FPACK    __FPOWER    * power(d0,d1)
  1569.     bcs    Eover2
  1570.     move.l    d0,d2
  1571.     rts
  1572. *
  1573. Egt2F:
  1574.     FPACK    __FCMP        * float 比較
  1575.     sgt    d2
  1576.     bra    E1
  1577. Elt2F:
  1578.     FPACK    __FCMP        * float 比較
  1579.     slt    d2
  1580.     bra    E1
  1581. Eequ2F:
  1582.     FPACK    __FCMP        * float 比較
  1583.     seq    d2
  1584.     bra    E1
  1585. Ene2F:
  1586.     FPACK    __FCMP        * float 比較
  1587.     sne    d2
  1588.     bra    E1
  1589. Ege2F:
  1590.     FPACK    __FCMP        * float 比較
  1591.     sge    d2
  1592.     bra    E1
  1593. Ele2F:
  1594.     FPACK    __FCMP        * float 比較
  1595.     sle    d2
  1596. E1:    moveq.l    #1,d0
  1597.     and.l    d2,d0
  1598.     FPACK    __LTOF        * signed int → float ;    d0 = d0
  1599.     move.l    d0,d2
  1600.     rts
  1601.  
  1602. AndOrF:
  1603.     FPACK    __FTST        * v1==0?
  1604.     sne    d2
  1605.     move.l    d1,d0
  1606.     FPACK    __FTST        * v2==0?
  1607.     sne    d1
  1608.     rts
  1609.  
  1610. Eand2F:
  1611.     bsr    AndOrF
  1612.     and.b    d1,d2
  1613.     sne    d2
  1614.     bra    E1
  1615. Eor2F:
  1616.     bsr    AndOrF
  1617.     or.b    d1,d2
  1618.     sne    d2
  1619.     bra    E1
  1620.  
  1621. *---------------------------------------------
  1622.  
  1623. EnzanRead:
  1624. * 演算子&括弧読み取り
  1625. * unchar *EnzanRead(unchar *str,unsint *no)
  1626.     * 数字や>=0x7fの演算子はない
  1627.     lea    ENmes(pc),a2    * 演算子名表
  1628.     move.l    4(sp),a1    * str
  1629.     move.b    (a1),d0        * c=*str ; 1文字目
  1630.     cmp.b    #'0',d0
  1631.     bcs    @f        * <'0'
  1632.     * >='0'
  1633.     cmp.b    #'9',d0
  1634.     bls    ERret        * <='9' : 0~9は演算子としてありえない
  1635.     cmp.b    #$7f,d0
  1636.     bcc    ERret        * >=$7f : ここの部分も演算子としてありえない
  1637.     *
  1638. @@:    lea    enzansi(pc),a0    * code.w
  1639. 2:    move.w    (a0)+,d0    * code
  1640.     beq    ERret        * NULL(end of table) -> return(NULL)
  1641.     move.l    4(sp),a1    * s=str
  1642. 4:    cmp.b    #2,(a2)        * *e<=2?
  1643.     bls    3f        * Yes : 一致
  1644.     move.b    (a1)+,d1    * *s
  1645.     cmp.b    #'Z',d1        * >'Z'
  1646.     bhi    @f
  1647.     cmp.b    #'A',d1        * <'A'
  1648.     bcs    @f
  1649.     * 英大文字のみ
  1650.     or.b    #$20,d1        * 小文字化
  1651. @@:    cmp.b    (a2)+,d1
  1652.     beq    4b
  1653.     * 次の演算子
  1654. @@:    cmp.b    #2,(a2)+
  1655.     bhi    @b        * (a2)>2
  1656.     bra    2b
  1657. *
  1658. 3:    * 一致
  1659.     move.b    (a2),ifflag    * 演算子有効範囲
  1660.     move.l    8(sp),a2    * *no
  1661.     move.w    d0,(a2)        * *no=code
  1662.     move.l    a1,d0        * return(s)
  1663. 1:    *
  1664.     rts
  1665.  
  1666. ERret:    moveq.l    #0,d0        * return(NULL)
  1667.     rts
  1668.  
  1669. *---------------------------------------------
  1670.  
  1671. Yusen:
  1672. * 演算子優先順位:順位が高いものほど数字が大きい
  1673. * int Yusen(unint c)
  1674.     move.w    4+2(sp),d2
  1675.     * float用関数は全て特別優先順位
  1676.     cmp.w    #FeMin,d2    * >=$fexx?
  1677.     bcs    @f        * No
  1678.     moveq.l    #65,d0        * 優先順位65(乗除剰余の上、単項演算子の下)
  1679.     rts
  1680. *
  1681. @@:    lea    Lvs_1(pc),a0
  1682.     moveq.l    #10,d0        * lv=10
  1683. @@:    move.w    (a0)+,d1    * cc
  1684.     cmp.w    #$ffff,d1
  1685.     beq    1f        * end of table
  1686.     cmp.w    d2,d1        * 演算子内部コード一致?
  1687.     beq    2f        * 見つかった
  1688.     tst.w    d1        * cc==0?
  1689.     bne    @b        * No
  1690.     * =0
  1691.     add.l    #10,d0        * lv+=10
  1692.     bra    @b
  1693. *
  1694. 1:    * 見つからない
  1695.     moveq.l    #0,d0
  1696. 2:    rts
  1697.  
  1698. *---------------------------------------------
  1699.  
  1700. Dainyu:
  1701. * 変数への代入処理
  1702. * int Dainyu(long v2)
  1703. * return : 0=ok , <>0=VS*エラーコード
  1704.     lea    Vsikis(pc),a0
  1705.     moveq.l    #0,d0        * for .w = .l
  1706.     move.w    vs(a0),d0    * vs
  1707.     subq.l    #1,d0        * vs-1
  1708.     add.l    d0,d0
  1709.     add.l    d0,d0        * *4
  1710.     move.l    pstack(a0),a1    * pstack
  1711.     move.l    (a1,d0.l),d0    * p=pstack[vs-1]
  1712.     beq    4f        * p=0 : error
  1713.     bpl    @f        * p>=0
  1714.     * p<0 : 未確定変数
  1715.     neg.l    d0        * p=-p; 未確定->確定代入
  1716. @@:    * ここでは数値代入しかできない
  1717.     * if (var_num_write(p,v2,0/*0=整数,1=単精度実数*/)<0) return(-2);
  1718.     tst.b    ffloat
  1719.     sne.b    d2
  1720.     moveq.l    #1,d1
  1721.     and.l    d1,d2        * 整数=0,実数=1
  1722.     tst.b    ftei
  1723.     beq    @f
  1724.     * 定数定義モード(初期式ファイル)
  1725.     or.l    #BIT15|VDAI,d2    * 強制再定義&再定義不可モード
  1726. @@:    move.l    4(sp),d1    * v2
  1727.     movem.l    d0/d1/d2,-(sp)
  1728. *    move.l    d2,-(sp)    * VTYPE=0/1,BIT15
  1729. *    move.l    d1,-(sp)    * v2
  1730. *    move.l    d0,-(sp)    * p
  1731.     bsr    var_num_write
  1732.     lea    4*3(sp),sp
  1733.     tst.l    d0
  1734.     bmi    2f        * 再代入不可
  1735.     moveq.l    #0,d0        * return(0)
  1736.     rts
  1737.  
  1738. 2:    * 再代入不可ならエラー
  1739.     moveq.l    #VARCSTA,d0
  1740.     rts
  1741.  
  1742. 4:    * p=0 : 数値に代入しようとした
  1743.     moveq.l    #VSNUMST,d0
  1744.     rts
  1745.  
  1746. *---------------------------------------------
  1747.  
  1748. _vsiki:
  1749.     link a6,#-30
  1750.     movem.l d3/d4/d5/d6/d7/a3/a4/a5,-(sp)
  1751.     moveq.l #0,d2
  1752.     move.l d2,-14(a6)
  1753.     clr.w d5
  1754.     move.w d5,d6
  1755.     moveq.l #1,d4
  1756.     lea Vsikis(pc),a0
  1757.     move.w d5,es(a0)
  1758.     move.w d5,vs(a0)
  1759.     move.l 8(a6),a1
  1760.     move.l (a1),a5
  1761.     move.l #Vsikis,d7
  1762.     move.l d7,d2
  1763.     addq.l #6,d2
  1764.     move.l d2,-22(a6)
  1765.     move.l d7,a4
  1766.     addq.w #4,a4
  1767.     move.l d7,d2
  1768.     addq.l #8,d2
  1769.     move.l d2,-26(a6)
  1770.     move.l d7,d2
  1771.     addq.l #2,d2
  1772.     move.l d2,-30(a6)
  1773.     jbra ?228
  1774. ?263:
  1775.     cmp.b #32,d3
  1776.     jbeq ?232
  1777.     cmp.b #9,d3
  1778.     jbne ?231
  1779. ?232:
  1780.     addq.w #1,a5
  1781.     jbra ?228
  1782. ?231:
  1783.     pea -2(a6)
  1784.     move.l a5,-(sp)
  1785.     jbsr EnzanRead
  1786.     move.l d0,d1
  1787.     addq.w #8,sp
  1788.     jbeq ?233        * NULL
  1789.     * float
  1790.     move.b    ifflag(pc),d0
  1791.     tst.b    ffloat
  1792.     beq    @f
  1793.     * 実数時
  1794.     tst.b    d0        * 両方使える演算子?
  1795.     beq    10f        * Yes
  1796.     cmp.b    #2,d0        * 実数で使える演算子?
  1797.     beq    10f        * Yes
  1798.     moveq.l    #VSIONLY,d0    * 整数時しか使えない
  1799.     bra    ?227        * error
  1800.     *
  1801. @@:    * 整数時
  1802.     cmp.b    #1,d0
  1803.     bls    10f        * <=1は大丈夫
  1804.     * ifflag=2 ; floatのみの関数である
  1805.     moveq.l    #VSFONLY,d0    * float時しか使えない
  1806.     bra    ?227        * error
  1807. *
  1808. 10:    move.l d1,a5
  1809.     move.w -2(a6),d1
  1810.     moveq.l #0,d0
  1811.     move.w d1,d0
  1812.     moveq.l #40,d2
  1813.     cmp.l d0,d2
  1814.     jbeq ?249
  1815.     moveq.l #41,d2
  1816.     cmp.l d0,d2
  1817.     jbeq ?252
  1818.     tst.l -14(a6)
  1819.     jbge ?236
  1820.     cmp.w #61,d1
  1821.     jbeq ?236
  1822.     moveq.l #52,d0
  1823.     jbra ?227
  1824. ?236:
  1825.     clr.w d5
  1826.     move.w d5,d6
  1827.     tst.w d4
  1828.     jbeq ?237
  1829.     cmp.w #45,-2(a6)
  1830.     jbne ?238
  1831.     move.w #64,-2(a6)
  1832. ?238:
  1833.     cmp.w #43,-2(a6)
  1834.     jbne ?237
  1835.     clr.w d4
  1836.     jbra ?228
  1837. ?237:
  1838.     move.l -22(a6),a1
  1839.     tst.w (a1)
  1840.     jbne ?240
  1841.     move.w -2(a6),d0
  1842.     cmp.w #64,d0        * @=VMINUS
  1843.     jbeq ?240
  1844.     cmp.w #33,d0        * '!'
  1845.     jbeq ?240
  1846.     cmp.w #126,d0        * '~'
  1847.     jbeq ?240
  1848.     cmp.w #65023,d0        * 関数;$fe00
  1849.     jbhi ?240
  1850.     moveq.l #3,d0
  1851.     jbra ?227
  1852. ?240:
  1853.     tst.w (a4)
  1854.     jble ?241
  1855.     move.w -2(a6),d4
  1856.     jbra ?242
  1857. ?245:
  1858.     moveq.l #0,d0
  1859.     move.w d4,d0
  1860.     move.l d0,-(sp)
  1861.     lea Yusen(pc),a3
  1862.     jbsr (a3)
  1863.     move.l d0,d3
  1864.     move.w (a4),d0
  1865.     ext.l d0
  1866.     add.l d0,d0
  1867.     move.l d0,a0
  1868.     move.l -26(a6),a1
  1869.     add.l (a1),a0
  1870.     moveq.l #0,d0
  1871.     move.w -2(a0),d0
  1872.     move.l d0,-(sp)
  1873.     jbsr (a3)
  1874.     addq.w #8,sp
  1875.     cmp.l d3,d0
  1876.     jblt ?241
  1877.     cmp.w #61,d4
  1878.     jbeq ?241
  1879.     jbsr Enzan
  1880.     move.l    d1,-6(a6)    * err
  1881.     tst.l d0
  1882.     jblt ?268
  1883.     move.w d0,d4
  1884. ?242:
  1885.     tst.w (a4)
  1886.     jbgt ?245
  1887. ?241:
  1888.     move.l d7,a1
  1889.     move.w (a1),d2
  1890.     cmp.w (a4),d2
  1891.     jbne ?246
  1892.     moveq.l #6,d0
  1893.     jbra ?227
  1894. ?246:
  1895.     move.w (a4),d0
  1896.     ext.l d0
  1897.     move.l -26(a6),a1
  1898.     move.l (a1),a0
  1899.     add.l d0,d0
  1900.     move.w -2(a6),(a0,d0.l)
  1901.     addq.w #1,(a4)
  1902.     cmp.w #64,-2(a6)
  1903.     jbne ?247
  1904.     clr.w d0
  1905.     jbra ?248
  1906. ?247:
  1907.     moveq.l #2,d0
  1908. ?248:
  1909.     move.w d0,d4
  1910.     moveq.l #0,d2
  1911.     move.l d2,-14(a6)
  1912.     jbra ?228
  1913. ?249:
  1914.     cmp.w #1,d6
  1915.     jbne ?250
  1916.     moveq.l #9,d0
  1917.     jbra ?227
  1918. ?250:
  1919.     move.l d7,a1
  1920.     move.w (a1),d2
  1921.     cmp.w (a4),d2
  1922.     jbne ?251
  1923.     moveq.l #7,d0
  1924.     jbra ?227
  1925. ?251:
  1926.     move.w (a4),d0
  1927.     ext.l d0
  1928.     move.l -26(a6),a1
  1929.     move.l (a1),a0
  1930.     add.l d0,d0
  1931.     move.w -2(a6),(a0,d0.l)
  1932.     addq.w #1,(a4)
  1933.     clr.w d6
  1934.     moveq.l #1,d5
  1935.     moveq.l #3,d4
  1936.     jbra ?228
  1937. ?252:
  1938.     cmp.w #1,d5
  1939.     jbne ?254
  1940.     moveq.l #10,d0
  1941.     jbra ?227
  1942. ?258:
  1943.     jbsr Enzan
  1944.     move.l    d1,-6(a6)    * err
  1945.     tst.l d0
  1946.     jblt ?268
  1947.     tst.w (a4)
  1948.     jbne ?254
  1949.     moveq.l #8,d0
  1950.     jbra ?227
  1951. ?254:
  1952.     move.w (a4),d0
  1953.     ext.l d0
  1954.     add.l d0,d0
  1955.     move.l d0,a0
  1956.     move.l -26(a6),a1
  1957.     add.l (a1),a0
  1958.     cmp.w #40,-2(a0)
  1959.     jbne ?258
  1960.     subq.w #1,(a4)
  1961.     clr.w d5
  1962.     move.w d5,d4
  1963.     move.w d5,d6
  1964.     jbra ?228
  1965. ?233:
  1966.     cmp.w #1,d6
  1967.     jbne ?260
  1968.     moveq.l #2,d0
  1969.     jbra ?227
  1970. ?260:
  1971.     move.l -30(a6),a1
  1972.     move.w (a1),d2
  1973.     move.l -22(a6),a1
  1974.     cmp.w (a1),d2
  1975.     jbne ?261
  1976.     moveq.l #5,d0
  1977.     jbra ?227
  1978. ?261:
  1979.     pea -18(a6)
  1980.     pea -14(a6)
  1981.     pea -10(a6)
  1982.     move.l a5,-(sp)
  1983.     jbsr _NumVarRead
  1984.     move.l d0,d1
  1985.     lea 16(sp),sp
  1986.     jbne ?262
  1987.     move.l -18(a6),d0
  1988.     jbra ?227
  1989. ?262:
  1990.     move.l -22(a6),a1
  1991.     move.w (a1),d0
  1992.     ext.l d0
  1993.     move.l d7,a1
  1994.     move.l 16(a1),a0
  1995.     asl.l #2,d0
  1996.     move.l -14(a6),(a0,d0.l)
  1997.     move.l -22(a6),a1
  1998.     move.w (a1),d0
  1999.     ext.l d0
  2000.     move.l d7,a1
  2001.     move.l 12(a1),a0
  2002.     asl.l #2,d0
  2003.     move.l -10(a6),(a0,d0.l)
  2004.     move.l -22(a6),a1
  2005.     addq.w #1,(a1)
  2006.     moveq.l #1,d6
  2007.     clr.w d5
  2008.     move.w d5,d4
  2009.     move.l d1,a5
  2010. ?228:
  2011.     move.b (a5),d3
  2012.     moveq.l #0,d0
  2013.     tst.b d3
  2014.     jbeq ?230
  2015.     cmp.b #44,d3
  2016.     jbeq ?230
  2017.     cmp.b #10,d3
  2018.     jbeq ?230
  2019.     cmp.b #164,d3
  2020.     jbeq ?230
  2021.     moveq.l #1,d0
  2022. ?230:
  2023.     tst.l d0
  2024.     jbne ?263
  2025.     tst.l -14(a6)
  2026.     jbge ?264
  2027.     moveq.l #51,d0
  2028.     jbra ?227
  2029. ?264:
  2030.     move.l #Vsikis,d0
  2031.     move.l d0,a3
  2032.     addq.w #4,a3
  2033.     move.l d0,a4
  2034.     addq.w #8,a4
  2035.     jbra ?265
  2036. ?270:
  2037.     jbsr Enzan
  2038.     move.l    d1,-6(a6)    * err
  2039.     tst.l d0
  2040.     jbge ?265
  2041.     moveq.l #-1,d2
  2042.     cmp.l -6(a6),d2
  2043.     jbne ?268
  2044.     move.w (a3),d0
  2045.     ext.l d0
  2046.     add.l d0,d0
  2047.     move.l d0,a0
  2048.     add.l (a4),a0
  2049.     cmp.w #40,-2(a0)
  2050.     jbne ?268
  2051.     moveq.l #12,d0
  2052.     jbra ?227
  2053. ?268:
  2054.     move.l -6(a6),d0
  2055.     jbra ?227
  2056. ?265:
  2057.     tst.w (a3)
  2058.     jbgt ?270
  2059.     moveq.l #12,d2
  2060.     add.l #Vsikis,d2
  2061.     move.l d2,a0
  2062.     move.l (a0),a0
  2063.     move.l 12(a6),a1
  2064.     move.l (a0),(a1)
  2065.     cmp.b #44,d3
  2066.     jbeq ?272
  2067.     cmp.b #164,d3
  2068.     jbeq ?272
  2069.     cmp.b #10,d3
  2070.     jbne ?271
  2071. ?272:
  2072.     addq.w #1,a5
  2073. ?271:
  2074.     move.l 8(a6),a1
  2075.     move.l a5,(a1)
  2076.     moveq.l #0,d0
  2077.     cmp.b #44,d3
  2078.     jbeq ?274
  2079.     cmp.b #164,d3
  2080.     jbeq ?274
  2081.     cmp.b #10,d3
  2082.     jbne ?273
  2083. ?274:
  2084.     moveq.l #1,d0
  2085. ?273:
  2086.     neg.l d0
  2087. ?227:
  2088.     movem.l -62(a6),d3/d4/d5/d6/d7/a3/a4/a5
  2089.     unlk a6
  2090.     rts
  2091.  
  2092. *---------------------------------------------
  2093.  
  2094. var_dump:
  2095. * 変数領域ダンプ
  2096. * void var_dump()
  2097. regs    .reg    d3-d6/a3-a4
  2098.     movem.l    regs,-(sp)
  2099.     move.w    base(pc),d0
  2100.     lea    bases(pc),a0    * その時の表示進数に従う
  2101.     moveq.l    #0,d4        * for .b = .l
  2102.     move.b    (a0,d0.w),d4    * bs=bases[base]
  2103.     moveq.l    #0,d6        * for .b = .w
  2104.     lea    Bsym(pc),a0
  2105.     move.b    (a0,d0.w),d6    * $%@
  2106.     *
  2107.     lea    var(pc),a0
  2108.     move.l    vlots(a0),d3    * vlots
  2109.     beq    7f        * 変数がない
  2110.     move.l    vwork(a0),a3    * vwork
  2111.     addq.l    #VTOP,a3    * &vwork[VTOP]
  2112.     *
  2113. 5:    bsr    PrCRLF        * 最初の改行
  2114.     pea    Vname(a3)    * vname
  2115.     DOS    _PRINT        * 変数名
  2116.     addq.l    #4,sp
  2117.     bsr    PrTAB
  2118.     *
  2119.     pea    Vnum(a3)
  2120.     bsr    ctol        * d0.l=num
  2121.     addq.l    #4,sp
  2122.     move.l    d0,d5
  2123.     *
  2124.     move.b    Vmd(a3),d0    * md
  2125.     moveq.l    #VKAKU,d1
  2126.     and.b    d0,d1
  2127.     beq    @f        * 確定
  2128.     * 未確定
  2129.     pea    MesMikaku(pc)
  2130.     bra    6f
  2131. *
  2132. @@:    * 確定
  2133.     clr.b    c        * エラー無しの印
  2134.     lea    MesDeni(pc),a4
  2135.     and.b    #VTYPE,d0
  2136.     beq    v2        * 整数
  2137.     * 実数
  2138.     lea    MesDenf(pc),a4
  2139.     cmp.l    #10,d4        * 10進数?
  2140.     bne    @f        * No
  2141.     * 実数10進表示
  2142.     lea    kbuf(pc),a0    * 流用
  2143.     move.l    d5,d0        * num
  2144.     moveq.l    #Yuketa,d2    * 全体の桁数
  2145.     FPACK    __FGCVT
  2146.     pea    kbuf(pc)
  2147.     bra    6f        * 表示へ
  2148. *
  2149. @@:    * 実数10進以外
  2150.     tst.b    fnai
  2151.     bne    v2        * ->内部表現表示
  2152.     * 整数化表示
  2153.     move.l    d5,d0
  2154.     FPACK    __FTOL        * float(d0) -> int(d0)
  2155.     scs.b    c        * 整数化出来ないの印
  2156.     bcs    v2        * 整数化出来ない時はしない
  2157. @@:    move.l    d0,d5
  2158.     *
  2159. v2:    * 整数はいきなりここへ来る
  2160.     move.l    d4,-(sp)    * 表示進数
  2161.     pea    kbuf(pc)    * kbufを流用
  2162.     move.l    d5,-(sp)    * num
  2163.     bsr    make_base    * ret=d0
  2164.     lea    4*3(sp),sp
  2165.     lea    kbuf(pc),a0
  2166.     add.l    d0,a0        * &kbuf[ret]
  2167.     * 進数記号表示
  2168.     cmp.l    #10,d4
  2169.     beq    @f
  2170.     move.w    d6,-(sp)
  2171.     DOS    _PUTCHAR    * d6.bのみ表示される
  2172.     addq.l    #2,sp
  2173. @@:    pea    (a0)
  2174. 6:    DOS    _PRINT        * 数値表示
  2175.     bsr    PrTAB
  2176.     pea    (a4)        * 整数/実数
  2177.     DOS    _PRINT
  2178.     addq.l    #8,sp
  2179.     *
  2180.     tst.b    c        * 整数化出来てる?
  2181.     beq    @f
  2182.     * 整数化出来てない
  2183.     move.w    #'(',-(sp)
  2184.     DOS    _PUTCHAR
  2185.     pea    MVARCCINT(pc)
  2186.     DOS    _PRINT        * "(整数化出来ない)"を表示
  2187.     move.w    #')',-(sp)
  2188.     DOS    _PUTCHAR
  2189.     addq.l    #8,sp
  2190. @@:    *
  2191.     btst.b    #BVDAI,Vmd(a3)    * md&VDAI?
  2192.     beq    @f
  2193.     bsr    PrTAB
  2194.     pea    MesTeisu(pc)    * 定数=再代入不可
  2195.     DOS    _PRINT
  2196.     addq.l    #4,sp
  2197. @@:    *
  2198.     moveq.l    #0,d0        * for .b=.l
  2199.     move.b    (a3)+,d0    * len
  2200.     addq.l    #sizeV,d0    * len(1):md(1):num(4):vname(len):EOS
  2201.     add.l    d0,a3        * 次の変数へ
  2202.     *
  2203.     subq.l    #1,d3        * 変数がある間
  2204.     bne    5b
  2205.     *
  2206.     bsr    PrCRLF        * 最後の改行
  2207. 7:    movem.l    (sp)+,regs
  2208.     rts
  2209.  
  2210. PrTAB:    move.w    #TAB,-(sp)
  2211.     DOS    _PUTCHAR    * TAB
  2212.     addq.l    #2,sp
  2213.     rts
  2214.  
  2215. PrCRLF:    pea    CrLf2(pc)
  2216.     DOS    _PRINT        * 改行
  2217.     addq.l    #4,sp
  2218.     rts
  2219.  
  2220. *---------------------------------------------
  2221.  
  2222. FGETSs:
  2223. * int FGETSs(unchar *buf,int max,int fp)
  2224. *        4       8      12
  2225.     * FGETCは入力がないと待ってしまうので、EOF無しファイルに対応させるには
  2226.     * READを使うしかない(たぶん遅くなってしまうけど)
  2227. regs    .reg    d3/d4/d5
  2228. ofs    =    (4*3)
  2229.     movem.l    regs,-(sp)
  2230.     move.l    4+ofs(sp),a1    * buf
  2231.     move.l    8+ofs(sp),d3    * max
  2232.     move.l    12+ofs(sp),d4    * fp
  2233.     moveq.l    #0,d2        * cc=0
  2234.     moveq.l    #0,d5        * len=0
  2235.     *
  2236. 1:    pea    1.w        * 1バイト読み込み
  2237.     pea    c(pc)        * &c
  2238.     move.w    d4,-(sp)    * fp
  2239.     DOS    _READ        * ret=d0.l
  2240.     lea    10(sp),sp
  2241.     tst.l    d0
  2242.     ble    2f        * ret<=0
  2243.     move.b    c(pc),d1
  2244.     cmp.b    #$1a,d1
  2245.     beq    2f        * c=$1a
  2246.     cmp.b    #$0a,d1
  2247.     beq    2f        * c=$0a
  2248.     move.b    d1,(a1)+    * *buf++=c
  2249.     addq.l    #1,d5        * len++
  2250.     cmp.l    d3,d5        * len>=max?
  2251.     bcc    3f        * Yes : バッファーオーバー
  2252.     move.b    d1,d2        * cc=c ; 1つ前のコード記録
  2253.     bra    1b
  2254. *
  2255. 3:    moveq.l    #-2,d0        * バッファーオーバー
  2256.     bra    4f
  2257. *
  2258. 2:    cmp.b    #$0d,d2        * cc=$0d?
  2259.     bne    @f        * No
  2260.     subq.l    #1,a1        * Yes : buf-- ; CRLFは両方消す
  2261. @@:    clr.b    (a1)        * *buf=EOS
  2262.     tst.l    d0        * ret==0?
  2263.     seq    d0
  2264.     cmp.b    #$1a,d1        * c=$1a?
  2265.     seq    d1
  2266.     or.b    d1,d0
  2267.     moveq.l    #1,d1
  2268.     and.l    d1,d0        * 1/0
  2269.     neg.l    d0        * -1/0 : EOFかどうか
  2270. 4:    movem.l    (sp)+,regs
  2271.     rts
  2272.  
  2273. *---------------------------------------------
  2274.  
  2275. vsiki_read:
  2276. * 1行内継続付き式評価処理
  2277. * int vsiki_read(unchar *line,long *num,unchar *(*err))
  2278. *            4    8        12
  2279.     move.l    4(sp),a0    * line
  2280.     subq.l    #1,a0        * 次で+1するため
  2281. 3:    addq.l    #1,a0
  2282. 1:    moveq.l    #0,d0        * return(0)のため
  2283.     * セパレータースキップ
  2284.     move.b    (a0),d1
  2285.     beq    2f        * EOS : 式評価終了
  2286.     cmp.b    #SPC,d1
  2287.     beq    3b
  2288.     cmp.b    #TAB,d1
  2289.     beq    3b
  2290.     *
  2291.     move.l    12(sp),a2    * *err
  2292.     move.l    a0,(a2)        * *err=line; エラー発生点保持のため
  2293.     move.l    a0,line
  2294.     move.l    8(sp),-(sp)    * num
  2295.     pea    line(pc)
  2296.     bsr    _vsiki        * ret=vsiki(&line,num);
  2297.     addq.l    #8,sp
  2298.     move.l    line(pc),a0
  2299.     tst.l    d0
  2300.     bmi    1b        * <0
  2301. 2:    rts
  2302.  
  2303. *---------------------------------------------
  2304.  
  2305. _vsiki_readF:
  2306.     link a6,#-272
  2307.     movem.l d3/d4/d5/a3/a4,-(sp)
  2308.     move.l 12(a6),d5
  2309.     move.l 16(a6),a0
  2310.     move.l 20(a6),a4
  2311.     move.l 24(a6),a3
  2312.     moveq.l    #-1,d3
  2313.     tst.b (a0)
  2314.     jbeq ?312
  2315.     lea -90(a6),a1
  2316. ?305:
  2317.     move.b (a0)+,(a1)+
  2318.     jbne ?305
  2319.     move.w #32,-(sp)
  2320.     pea -90(a6)
  2321.     pea -272(a6)
  2322.     DOS    _FILES
  2323.     lea 10(sp),sp
  2324.     tst.l d0
  2325.     jblt ?308
  2326.     move.l (a3),d2
  2327.     cmp.l -246(a6),d2
  2328.     jbne ?310
  2329.     move.w -250(a6),d2
  2330.     cmp.w 6(a3),d2
  2331.     jbne ?310
  2332.     move.w -248(a6),d2
  2333.     cmp.w 4(a3),d2
  2334.     jbeq ?312
  2335. ?310:
  2336.     move.l -246(a6),(a3)
  2337.     move.w -248(a6),4(a3)
  2338.     move.w -250(a6),6(a3)
  2339.     st.b    ftei        * 定数モード(起動時式ファイル)
  2340.     jbra ?311
  2341. ?318:
  2342.     addq.l #1,8(a6)
  2343. ?314:
  2344.     move.l 8(a6),a0
  2345.     move.b (a0),d0
  2346.     moveq.l #0,d1
  2347.     cmp.b #32,d0
  2348.     jbeq ?317
  2349.     cmp.b #9,d0
  2350.     jbne ?316
  2351. ?317:
  2352.     moveq.l #1,d1
  2353. ?316:
  2354.     tst.l d1
  2355.     jbne ?318
  2356.     tst.b d0
  2357.     jbne ?319
  2358.     moveq.l #0,d3
  2359.     jbra ?313
  2360. ?319:
  2361.     cmp.b #63,d0
  2362.     jbeq ?320
  2363.     move.l 8(a6),(a4)
  2364.     move.l d5,-(sp)
  2365.     pea 8(a6)
  2366.     jbsr _vsiki
  2367.     move.l d0,d3
  2368.     addq.w #8,sp
  2369.     jbra ?312
  2370. ?320:
  2371.     lea -90(a6),a1
  2372.     move.l 8(a6),a0
  2373.     jbra ?322
  2374. ?325:
  2375.     move.b d0,(a1)+
  2376. ?322:
  2377.     addq.w #1,a0
  2378.     move.b (a0),d0
  2379.     moveq.l #0,d1
  2380.     cmp.b #32,d0
  2381.     jbeq ?324
  2382.     cmp.b #9,d0
  2383.     jbeq ?324
  2384.     cmp.b #10,d0
  2385.     jbeq ?324
  2386.     cmp.b #44,d0
  2387.     jbeq ?324
  2388.     cmp.b #164,d0
  2389.     jbeq ?324
  2390.     tst.b d0
  2391.     jbeq ?324
  2392.     moveq.l #1,d1
  2393. ?324:
  2394.     tst.l d1
  2395.     jbne ?325
  2396.     clr.b (a1)
  2397.     jbra ?326
  2398. ?329:
  2399.     addq.w #1,a0
  2400. ?326:
  2401.     move.b (a0),d0
  2402.     moveq.l #0,d1
  2403.     cmp.b #10,d0
  2404.     jbeq ?328
  2405.     cmp.b #44,d0
  2406.     jbeq ?328
  2407.     cmp.b #164,d0
  2408.     jbeq ?328
  2409.     tst.b d0
  2410.     jbeq ?328
  2411.     moveq.l #1,d1
  2412. ?328:
  2413.     tst.l d1
  2414.     jbne ?329
  2415.     move.l a0,8(a6)
  2416. ?311:
  2417.     move.w #256,-(sp)
  2418.     pea -90(a6)
  2419.     DOS    _OPEN
  2420.     move.l d0,d4
  2421.     addq.w #6,sp
  2422.     jbge ?331
  2423. ?308:
  2424.     moveq.l #-1,d2
  2425.     move.l d2,(a3)
  2426.     move.w d2,6(a3)
  2427.     move.w d2,4(a3)
  2428.     moveq.l #15,d3
  2429.     moveq.l #-90,d2
  2430.     add.l a6,d2
  2431.     move.l d2,8(a6)
  2432.     jbra ?313
  2433. ?341:
  2434.     lea -218(a6),a0
  2435.     jbra ?333
  2436. ?337:
  2437.     addq.w #1,a0
  2438. ?333:
  2439.     move.b (a0),d0
  2440.     moveq.l #0,d1
  2441.     cmp.b #32,d0
  2442.     jbeq ?336
  2443.     cmp.b #9,d0
  2444.     jbne ?335
  2445. ?336:
  2446.     moveq.l #1,d1
  2447. ?335:
  2448.     tst.l d1
  2449.     jbne ?337
  2450.     tst.b d0
  2451.     jbeq ?331
  2452.     cmp.b #10,d0
  2453.     jbeq ?331
  2454.     cmp.b #59,d0
  2455.     jbeq ?331
  2456.     move.l a4,-(sp)
  2457.     move.l d5,-(sp)
  2458.     move.l a0,-(sp)
  2459.     jbsr vsiki_read
  2460.     move.l d0,d3
  2461.     lea 12(sp),sp
  2462.     jbgt ?332
  2463. ?331:
  2464.     move.l d4,-(sp)
  2465.     pea 128.w
  2466.     pea -218(a6)
  2467.     jbsr FGETSs
  2468.     move.l d0,d3
  2469.     lea 12(sp),sp
  2470.     jbeq ?341
  2471. ?332:
  2472.     moveq.l #-2,d2
  2473.     cmp.l d3,d2
  2474.     jbne ?342
  2475.     moveq.l #16,d3
  2476.     move.l a6,d2
  2477.     add.l #-218,d2
  2478.     move.l d2,(a4)
  2479. ?342:
  2480.     clr.b    ftei        * 1回起動式ファイルを読んだら定数モードを解除
  2481.     move.w d4,-(sp)
  2482.     DOS    _CLOSE
  2483.     addq.w #2,sp
  2484.     tst.l d3
  2485.     jbgt ?313
  2486. ?312:
  2487.     tst.l d3
  2488.     jblt ?314
  2489. ?313:
  2490.     move.l d3,d0
  2491.     movem.l -292(a6),d3/d4/d5/a3/a4
  2492.     unlk a6
  2493.     rts
  2494.  
  2495. *---------------------------------------------
  2496.  
  2497. ErrorSearch:
  2498. * エラーメッセージサーチ
  2499. * unchar *ErrorSearch(int ecode)
  2500.     move.w    4+2(sp),d1    * ecode
  2501.     lea    ERRmes(pc),a1
  2502.     lea    ERRvsiki(pc),a0    * eno.w
  2503. @@:    move.w    (a0)+,d0    * eno
  2504.     beq    2f        * NULL -> end (NULLを返す)
  2505.     cmp.w    d0,d1        * eno==ecode?
  2506.     beq    1f        * 一致
  2507. 3:    tst.b    (a1)+        * to next mes
  2508.     bne    3b
  2509.     bra    @b
  2510. *
  2511. 1:    move.l    a1,d0
  2512.     rts            * return(mes)
  2513.  
  2514. 2:    moveq.l    #0,d0        * return(NULL)
  2515.     rts
  2516.  
  2517. *---------------------------------------------
  2518.  
  2519. VARINITS    macro
  2520. * 変数領域をクリアする
  2521. * なぜマクロにするのかはInitWorkを参照のこと
  2522. local    L1
  2523.     lea    var(pc),a1
  2524.     move.l    (a1),a0        * var.vwork
  2525.     clr.b    (a0)        * vwork[0]=0
  2526.     clr.l    vlots(a1)    * vlots=0
  2527.     * ハッシュテーブル初期化
  2528.     move.l    vhash(a1),a0    * var.vhash
  2529.     move.w    vhsize(a1),d0    * var.vhsize
  2530.     subq.w    #1,d0        * -1 for dbra
  2531. L1:    clr.l    (a0)+        * for (i=0;i<vhsize;i++) vhash[i]=0;
  2532.     dbra    d0,L1
  2533.     endm
  2534.  
  2535. VarInit:
  2536. * 変数領域をクリアする
  2537.     VARINITS
  2538.     * 次回起動時式ファイル読み込み必要
  2539.     moveq.l    #-1,d0
  2540.     move.l    d0,fsizeI
  2541.     move.l    d0,fdateI    * ftimeIもクリアする
  2542.     move.l    d0,fsizeF
  2543.     move.l    d0,fdateF    * ftimeFもクリアする
  2544.     rts
  2545.  
  2546. *---------------------------------------------
  2547.  
  2548. Deni:    * 整数
  2549.     move.w    #NOT_ASCII|XF1_KEY,xfkey+2    * 操作キーの変更
  2550.     clr.b    ffloat
  2551.     bra    Den
  2552. *
  2553. Denf:    * 実数
  2554.     move.w    #NOT_ASCII|XF2_KEY,xfkey+2    * 操作キーの変更
  2555.     st.b    ffloat
  2556.     clr.b    hugo            * 内部的には符号なし扱いになる
  2557. *
  2558. Den:    * 共通メインルーチン
  2559.     cmp.b    #$ff,first        * 前回エラー?
  2560.     bne    @f            * No
  2561.     * 前回エラーが出ているので、終了してしまう。
  2562.     * 入力ラインの修正が必要。
  2563.     move.b    #1,first
  2564.     move.l    #CACI_END,d0
  2565.     rts
  2566.     * 
  2567. @@:    move.w    4+2(sp),d2        * BIT16K キーコード
  2568.     move.l    d3,-(sp)        * push d3
  2569.     move.w    #CACI_NORMAL,d3        * ret=規定外キー入力の時のため
  2570.     *
  2571.     bsr    BREAKOFF
  2572.     *
  2573.     move.w    base(pc),d0
  2574.     lea    bases(pc),a0
  2575.     move.b    (a0,d0.w),d6        * bs=bases[base]
  2576.     *
  2577.     * キーを探して各ルーチンへ飛ぶ
  2578.     lea    Jtable(pc),a0
  2579.     move.w    d2,d1
  2580.     and.w    #NAKEY,d1
  2581. @@:    move.l    (a0)+,d0        * jump|code
  2582.     beq    @f            * -> end of table
  2583.     cmp.w    d1,d0            * =code?
  2584.     bne    @b            * no
  2585.     clr.b    eover            * オーバーフローフラグクリア
  2586.     swap    d0            * d0=jump
  2587.     jsr    -4(a0,d0.w)
  2588.     *
  2589. @@:    bsr    BREAKON
  2590.     *
  2591.     moveq.l    #0,d0            * for .w = .l
  2592.     move.w    d3,d0
  2593.     move.l    (sp)+,d3        * pop d3
  2594.     rts
  2595.  
  2596. *------------------------------------
  2597.  
  2598. Jtable:    * 各キー毎のジャンプテーブル(出てきやすい順に並べる)
  2599.     * jump先(offset),code
  2600.     * CTRL+SHIFT+XF1/XF2     : 起動/終了
  2601.     * ↑↓/XF1/SHIFT+XF1/XF2 : 表示進数選択
  2602.     * CR                     : 決定&終了
  2603.     * ESC                    : 終了
  2604. xfkey:    .dc.w    xf1key-$,NOT_ASCII|XF1_KEY    * <-ここがXF2_KEYに変わる
  2605.     .dc.w    crkey-$,CR
  2606.     .dc.w    downkey-$,NOT_ASCII|DOWN_KEY
  2607.     .dc.w    upkey-$,NOT_ASCII|UP_KEY
  2608.     .dc.w    esckey-$,ESC
  2609.     .dc.w    key0-$,'0'
  2610.     .dc.w    key2-$,'2'
  2611.     .dc.w    key6-$,'6'
  2612.     .dc.w    key8-$,'8'
  2613.     .dc.w    keyplus-$,'+'
  2614.     .dc.w    keyminus-$,'-'
  2615.     .dc.w    xf5key-$,NOT_ASCII|XF5_KEY
  2616.     .dc.w    f10-$,NOT_ASCII|FKEY10_KEY
  2617.     .dc.w    f1-$,NOT_ASCII|FKEY1_KEY
  2618.     .dc.w    0,0            * end of table
  2619.  
  2620. *------------------------------------
  2621.  
  2622. key0:    * '0' : 10進数表示
  2623.     move.w    #0,base
  2624.     bra    DEX
  2625.  
  2626. key6:    * '6' : 16進数表示
  2627.     move.w    #1,base
  2628.     bra    DEX
  2629.  
  2630. key2:    * '2' : 2進数表示
  2631.     move.w    #2,base
  2632.     bra    DEX
  2633.  
  2634. key8:    * '8' : 8進数表示
  2635.     move.w    #3,base
  2636.     bra    DEX
  2637.  
  2638. keyplus:    * '+' : 符号なし表示
  2639.     tst.b    ffloat
  2640.     bne    BEEP        * float時には無効
  2641.     clr.b    hugo
  2642.     bra    DEX
  2643.  
  2644. keyminus:    * '-' : 符号あり表示
  2645.     tst.b    ffloat
  2646.     bne    BEEP        * float時には無効
  2647.     st.b    hugo
  2648.     bra    DEX
  2649.  
  2650. f1:    * 内部表現表示切り替え
  2651.     tst.b    ffloat
  2652.     beq    BEEP        * 整数時には無効
  2653.     not.b    fnai
  2654.     bra    DEX
  2655.  
  2656. f10:    * 変数ダンプ
  2657.     bsr    var_dump
  2658.     rts
  2659.  
  2660. BEEP:    moveq.l    #7,d1
  2661.     IOCS    _B_PUTC
  2662.     rts
  2663.  
  2664. *------------------------------------
  2665.  
  2666. upkey:    * ↑
  2667.     move.w    base(pc),d0
  2668.     subq.w    #1,d0
  2669.     bpl    @f
  2670.     move.w    #BMAX-1,d0
  2671. @@:    move.w    d0,base
  2672.     bra    DEX
  2673. *
  2674. downkey:* ↓
  2675.     move.w    base(pc),d0
  2676.     addq.w    #1,d0
  2677.     cmp.w    #BMAX,d0
  2678.     bcs    @f        * <BMAX
  2679.     moveq.l    #0,d0
  2680. @@:    move.w    d0,base
  2681.     bra    DEX
  2682.  
  2683. xf5key:    * XF5 : 全角-半角
  2684.     not.b    fzen        * 交互変換
  2685.     bra    DEXZ
  2686.  
  2687. *------------------------------------
  2688.  
  2689. crkey:    * CR : 決定終了
  2690.     * すでにcbufに代入されているのでそれを返すだけ
  2691.     move.w    #DF_OUTSTR|CACI_END,d3    * 出力
  2692.     move.b    #1,first        * first=1
  2693.     rts
  2694.  
  2695. xf1key:    * XF1/XF2 : 起動
  2696.     btst.l    #B_CTRL_ON,d2        * btstは.b/.lしかないため
  2697.     bne    @f            * +CTRLである
  2698.     * +CTRLでない
  2699.     btst.l    #B_SHIFT_ON,d2        * btstは.b/.lしかないため
  2700.     bne    upkey            * +SHIFTである : ↑
  2701.     bra    downkey            * +SHIFTでない : ↓
  2702. *
  2703. @@:    * CTRL+...
  2704.     btst.l    #B_SHIFT_ON,d2        * btstは.b/.lしかないため
  2705.     beq    upkey            * +SHIFTはない : ↑
  2706.     * CTRL+SHIFT+XF1/XF2:起動
  2707.     tst.b    first
  2708.     bne    @f
  2709.     * 2回目はキャンセルで終了
  2710. esckey:    * ESC
  2711.     move.w    #CACI_END,d3        * 終了
  2712.     move.b    #1,first        * first=1
  2713.     rts
  2714. *
  2715. @@:    * 起動した -> 計算
  2716.     clr.b    first            * first=0(sf firstでも全く同じ;同サイズ/クロック)
  2717.     *
  2718.     lea    cbuf(pc),a0
  2719.     moveq.l    #0,d1            * for .b = .l
  2720.     move.b    (a0),d1
  2721.     bsr    kcheck1            * 1文字目が全角?
  2722.     beq    @f            * No : 半角化しない
  2723.     * 半角化
  2724.     pea    (a0)            * cbuf (des)
  2725.     pea    (a0)            * cbuf (src)
  2726.     pea    14.w
  2727.     DOS    _KNJCTRL        * 上書きで全角→半角
  2728.     lea    12(sp),sp
  2729.     *
  2730. @@:    * 式評価(連続)
  2731.     lea    cbuf(pc),a1
  2732.     cmp.b    #'、',(a1)        * '、'で始まる?
  2733.     beq    61f            * Yes
  2734.     cmp.b    #',',(a1)        * ','で始まる?
  2735.     bne    @f            * No
  2736. 61:    addq.l    #1,a1            * ','/'、'を飛ばして実行
  2737.     bsr    VarInit            * 変数クリア
  2738.     *
  2739. @@:    lea    preexecI(pc),a0        * 整数式ファイル
  2740.     lea    fsizeI(pc),a2        * 更新判定
  2741.     tst.b    ffloat            * 実数?
  2742.     beq    60f            * No
  2743.     lea    preexecF(pc),a0        * 実数式ファイル
  2744.     lea    fsizeF(pc),a2        * 更新判定
  2745. 60:    pea    (a2)
  2746.     pea    err(pc)
  2747.     pea    (a0)            * 式ファイル名
  2748.     pea    num(pc)
  2749.     pea    (a1)            * cbuf(変換ラインの式)
  2750.     bsr    _vsiki_readF        * -> d0.l(ret2)
  2751.     lea    20(sp),sp
  2752.     tst.l    d0
  2753.     ble    DEX            * ret2<=0
  2754.     *
  2755.     * エラー発生
  2756.     move.l    d0,-(sp)
  2757.     bsr    ErrorSearch        * -> d0.l : エラーメッセージ
  2758.     addq.l    #4,sp
  2759.     * ここでNULLが返ってくることがあるということは内部エラーである
  2760.     tst.l    d0            * NULL?
  2761.     bne    @f            * No
  2762.     move.l    #InErr,d0        * 内部エラー(念のため入れておく)
  2763. @@:    move.l    d0,a1
  2764.     move.l    #C_SIZE,d0
  2765.     lea    kbuf(pc),a3        * 一旦kbufに格納する
  2766. @@:    subq.l    #1,d0
  2767.     move.b    (a1)+,(a3)+
  2768.     bne    @b
  2769.     subq.l    #1,a3            * EOSに戻す
  2770.     addq.l    #1,d0
  2771.     lea    MesError(pc),a1        * セパレーター
  2772. @@:    subq.l    #1,d0
  2773.     move.b    (a1)+,(a3)+
  2774.     bne    @b
  2775.     subq.l    #1,a3            * EOSに戻す
  2776.     addq.l    #1,d0
  2777.     move.l    err(pc),a1        * エラー発生場所
  2778. @@:    subq.l    #1,d0
  2779.     bne    11f
  2780.     clr.b    (a3)+
  2781.     bra    12f
  2782. 11:    move.b    (a1)+,(a3)+
  2783.     bne    @b
  2784. 12:    lea    kbuf(pc),a1
  2785.     lea    cbuf(pc),a3        * kbuf->cbuf(エラーはcbufへ直接入れる)
  2786. @@:    move.b    (a1)+,(a3)+
  2787.     bne    @b
  2788.     st.b    first            * first=$ff
  2789.     bra    99f
  2790. *
  2791. DEX:    * 変換ラインに表示して選択
  2792.     * 数値 -> kbuf
  2793.     move.w    base(pc),d0
  2794.     lea    bases(pc),a0
  2795.     move.b    (a0,d0.w),d6        * bs=bases[base]
  2796.     moveq.l    #0,d0            * for .b = .l
  2797.     move.b    d6,d0
  2798.     *
  2799.     tst.b    hugo
  2800.     beq    @f            * 符号なし
  2801.     * 符号あり
  2802.     neg.l    d0            * d0=-d0
  2803. @@:    move.l    num(pc),d2        * 数字
  2804.     tst.b    ffloat            * 実数?
  2805.     beq    80f            * No -> 整数
  2806.     * 実数
  2807.     cmp.l    #10,d0            * 10進数?
  2808.     bne    81f            * No -> 2/8/16進数
  2809.     * 実数10進表示(常に普通表示)
  2810.     lea    cbuf0(pc),a0        * 一度cbuf0に作る
  2811.     move.l    d2,d0
  2812.     moveq.l    #Yuketa,d2        * 全体の桁数
  2813.     FPACK    __FGCVT            * floatだけ変換
  2814.     bra    DEXZ
  2815. *
  2816. 81:    * 実数2/8/16進表示
  2817.     tst.b    fnai            * 内部表現表示?
  2818.     bne    80f            * Yes
  2819.     * 普通表示->整数化表示
  2820.     move.l    d0,-(sp)
  2821.     move.l    d2,d0
  2822.     FPACK    __FTOL            * float(d0) -> int(d0)
  2823.     scs.b    eover            * 整数化出来ない時はc=$ffになる
  2824.     bcs    @f            * 整数化出来ない時は元のまま
  2825.     move.l    d0,d2            * 整数化出来た
  2826. @@:    move.l    (sp)+,d0        * 進数
  2827.     *
  2828. 80:    move.l    d0,-(sp)        * 進数
  2829.     pea    cbuf0(pc)        * 一度cbuf0に作る
  2830.     move.l    d2,-(sp)        * 数字
  2831.     bsr    make_base        * 数値文字列化->cbuf
  2832.     lea    12(sp),sp
  2833.     tst.l    d0            * ret2==0?
  2834.     beq    DEXZ            * Yes
  2835.     lea    cbuf0(pc),a0
  2836.     lea    (a0,d0.l),a1
  2837. @@:    move.b    (a1)+,(a0)+        * strcpy(cbuf,&cbuf[ret2]); // cbuf[0]からに入れるため
  2838.     bne    @b
  2839.     tst.b    eover            * 整数化出来ないエラーが出ている?
  2840.     beq    DEXZ            * No
  2841.     * 整数化出来ていない
  2842.     subq.l    #1,a0            * EOSを消すため
  2843.     move.b    #'(',(a0)+
  2844.     lea    MVARCCINT(pc),a1
  2845. @@:    move.b    (a1)+,(a0)+        * "(整数化出来ない)"を追加
  2846.     bne    @b
  2847.     move.b    #')',-1(a0)
  2848.     clr.b    (a0)            * EOS
  2849.     
  2850.     *
  2851. DEXZ:    * 全角-半角
  2852.     lea    cbuf0(pc),a0
  2853.     tst.b    fzen            * 全角化?
  2854.     bne    98f            * Yes
  2855.     * 半角化;実際はcbuf0->cbufだけ
  2856.     lea    cbuf(pc),a1
  2857. @@:    move.b    (a0)+,(a1)+
  2858.     bne    @b
  2859.     bra    99f
  2860. *
  2861. 98:    * 全角化
  2862.     pea    cbuf(pc)        * cbuf (des)
  2863.     pea    (a0)            * cbuf0 (src)
  2864.     pea    13.w
  2865.     DOS    _KNJCTRL        * 半角→全角
  2866.     lea    12(sp),sp
  2867.     *
  2868. 99:    lea    cbuf(pc),a0
  2869.     cmp.b    #$ff,first        * error?
  2870.     seq.b    d1
  2871.     moveq.l    #1,d0
  2872.     and.l    d0,d1            * エラーの時は反転表示
  2873.     *
  2874.     move.l    #kbuf,d0
  2875.     bsr    Str2MEANS
  2876.     * タイトル -> mbuf
  2877.     lea    Title(pc),a0
  2878.     moveq.l    #'+',d0
  2879.     tst.b    hugo
  2880.     beq    @f
  2881.     moveq.l    #'-',d0
  2882. @@:    move.b    d0,(a0)            * Title[0]=(hugo? '-':'+');
  2883.     moveq.l    #'0',d0
  2884.     cmp.b    #10,d6            * bs>=10?(実際には16のみ)
  2885.     bcs    @f            * No
  2886.     moveq.l    #'1',d0
  2887.     sub.b    #10,d6            * 16 -> 6 , 10 -> 0
  2888. @@:    move.b    d0,1(a0)        * Title[1]='0'+(bs>=10);
  2889.     add.b    #'0',d6
  2890.     move.b    d6,2(a0)        * Title[2]='0'+(bs%10);
  2891.     * 実数/整数表示
  2892.     moveq.l    #' ',d1
  2893.     move.w    #'整',d0        * 整数
  2894.     tst.b    ffloat
  2895.     beq    @f
  2896.     move.w    #'実',d0        * 実数(整数化)
  2897.     tst.b    fnai            * 内部表現表示?
  2898.     beq    @f
  2899.     moveq.l    #'*',d1            * 実数(内部表現)
  2900. @@:    move.w    d0,6(a0)        * Title[6,7]='整'/'実';
  2901.     move.b    d1,10(a0)        * Title[10]=' '/'*'
  2902.     *
  2903.     move.l    #mbuf,d0
  2904.     moveq.l    #1,d1            * 反転表示
  2905.     move.w    #DF_KWINSTR|DF_MWINSTR|CACI_NORMAL,d3
  2906.     * 以下サブルーチンにつながる        * mbuf[Str2MEAN(Title,mbuf,1)]=0;
  2907. Str2MEANS:
  2908. * buf[Str2MEAN(mes,buf,mode)]=0
  2909. * a0   <- mes
  2910. * d0.l <- buf
  2911. * d1.l <- mode (0=通常表示,1=反転表示)
  2912.     move.l    d1,-(sp)    * mode
  2913.     move.l    d0,-(sp)    * buf
  2914.     pea    (a0)        * mes
  2915.     pea    62.w
  2916.     DOS    _KNJCTRL
  2917.     lea    4*4(sp),sp
  2918.     move.l    -8(sp),a0    * buf
  2919.     add.w    d0,d0        * .w=MEAN
  2920.     clr.w    (a0,d0.w)    * buf[..]=0
  2921.     rts
  2922.  
  2923. ******************************************************************************
  2924. * ワーク2
  2925. ******************************************************************************
  2926. * ここに置くワークは、常駐後に使われるもの
  2927. * これらのワークエリアは常駐後に利用可能になるので、
  2928. * 以下の非常駐ルーチンからは参照しないこと
  2929. *--------------------------------------------------------------------
  2930. * オフセットテーブルの定義
  2931.     .offset    0
  2932. *--------------------------------------------------------------------
  2933.  
  2934. _brksts        .ds.w    1    * BREAKフラグ
  2935. _kbuf        .ds.w    K_SIZE    * 変換ラインへ
  2936. _mbuf        .ds.w    M_SIZE    * モード表示領域へ
  2937. _cbuf        .ds.b    C_SIZE    * 仮入力行 -> 入力行へ(半角/全角)
  2938. _cbuf0        .ds.b    C_SIZE    * 計算結果文字列(常に半角)
  2939. _num        .ds.l    1
  2940. _err        .ds.l    1
  2941. _line        .ds.l    1
  2942. _c        .ds.b    1
  2943. _eover        .ds.b    1    * 整数化でのオーバーフロー
  2944. _ifflag        .ds.b    1    * その演算子が整数/floatどちらで使えるか
  2945.     .even
  2946. _keep_end    .ds.w    0    * オフセットのみ
  2947.  
  2948. *--------------------------------------------------------------------
  2949. * 実際のワークエリアの定義
  2950. *--------------------------------------------------------------------
  2951.  
  2952.     .text    * .offset解除
  2953. work2:
  2954. brksts        equ    work2+_brksts
  2955. kbuf        equ    work2+_kbuf
  2956. mbuf        equ    work2+_mbuf
  2957. cbuf        equ    work2+_cbuf
  2958. cbuf0        equ    work2+_cbuf0
  2959. num        equ    work2+_num
  2960. err        equ    work2+_err
  2961. line        equ    work2+_line
  2962. c        equ    work2+_c
  2963. eover        equ    work2+_eover
  2964. ifflag        equ    work2+_ifflag    * float
  2965.  
  2966. *********************************************************************
  2967. * ワークエリア初期化
  2968. *********************************************************************
  2969. * ワークエリアを低位メモリーに取るとき、mallocではなく常駐メモリーを多く取って
  2970. * プログラムの後ろに付ける。これは、メモリーの分断を防ぐためである。
  2971. *
  2972. InitWork:
  2973. * a2.l <- 元のvwork
  2974. * d6.l <- 常駐サイズ
  2975.     VARINITS        * ワークエリア初期化
  2976.     * ワークエリアのクリアにおいて、initspで設定されたスタックも破壊してしまう。
  2977.     * このためこの中ではサブルーチン呼び出しが出来ない。
  2978.     * そのためにここに直接書いている(他でも使うのでマクロ化)。
  2979.     *
  2980.     tst.b    fhigh        * /H?
  2981.     bne    @f        * Yes
  2982.     * 低位メモリーの時;高位メモリーワーク解放
  2983.     pea    (a2)        * 元var.vwork
  2984.     DOS    _MFREE
  2985.     addq.w    #4,sp        * めんどうなのでエラー処理は省略
  2986. @@:    clr.w    -(sp)        * exit(0)相当
  2987.     move.l    d6,-(sp)    * 常駐サイズ
  2988.     DOS    _KEEPPR
  2989. InitWorkEnd:
  2990.  
  2991. * InitWorkが上のワークに含まれないとおかしくなるけど、今のサイズなら大丈夫だろう
  2992. *--------------------------------------------------------------------
  2993. * 転送ルーチンサイズ<ワークエリアサイズである
  2994. * 常駐部分最後
  2995.  
  2996. KEEP_END    equ    work2+_keep_end
  2997.  
  2998. ******************************************************************************
  2999. *    非常駐ルーチン
  3000. ******************************************************************************
  3001. * アクセサリ定義構造体
  3002. ******************************************************************************
  3003.  
  3004.     .even
  3005. ACdef:
  3006. * 整数
  3007.     .dc.w    KS_EDITING|KS_SELECT            * 仮入力時+仮確定時のみ
  3008.     .dc.w    NOT_ASCII|CTRL_ON|SHIFT_ON|XF1_KEY    * 呼びだしキー
  3009.     .dc.l    Deni                    * アクセサリーメイン
  3010.     .dc.l    cbuf
  3011.     .dc.l    kbuf
  3012.     .dc.l    mbuf
  3013.     * 1つの構造体のサイズは20バイト
  3014. * 実数
  3015.     .dc.w    KS_EDITING|KS_SELECT            * 仮入力時+仮確定時のみ
  3016.     .dc.w    NOT_ASCII|CTRL_ON|SHIFT_ON|XF2_KEY    * 呼びだしキー
  3017.     .dc.l    Denf                    * アクセサリーメイン
  3018.     .dc.l    cbuf
  3019.     .dc.l    kbuf
  3020.     .dc.l    mbuf
  3021.  
  3022. ******************************************************************************
  3023. * 式・変数処理初期化
  3024. ******************************************************************************
  3025.  
  3026. Vsopen1:
  3027.     move.l    4(sp),d0        * vsize
  3028.     * vsizeの補正は外部で行われているのでここでは行わない
  3029.     lea    var(pc),a0
  3030.     move.l    d0,vwsize(a0)        * var.vwsize
  3031.     move.l    d0,a1            * vwsize
  3032.     *
  3033.     * ハッシュエリアサイズ計算(16bitサイズ)
  3034.     lsr.l    #4,d0            * d0/16
  3035.     cmp.l    #65536,d0
  3036.     bcs    @f            * <65536(16bit)
  3037.     move.l    #65535,d0        * max 65535
  3038. @@:    cmp.l    #1024,d0
  3039.     bcc    @f            * >=1024
  3040.     move.l    #1024,d0        * min 1024
  3041. @@:    move.w    d0,vhsize(a0)        * var.vhsize
  3042.     add.l    d0,d0
  3043.     add.l    d0,d0            * vhsize*LLONG
  3044.     add.l    d0,a1            * vwsize+vhsize*LLONG
  3045.     *
  3046.     * ワークエリアサイズ計算(変数/ハッシュ一括/全スタック確保)
  3047.     lea    Vsikis(pc),a0
  3048.     move.w    emax(a0),d0        * emax
  3049.     add.w    d0,a1
  3050.     add.w    d0,a1            * +emax*LSHORT(2) : estack.w
  3051.     moveq.l    #0,d0            * for .w = .l
  3052.     move.w    vmax(a0),d0        * vmax
  3053.     lsl.l    #3,d0            * *8(LLONG*2)    : vstack.l+pstack.l
  3054.     add.l    d0,a1
  3055.     move.l    a1,d0            * ret
  3056.     rts
  3057.  
  3058. *--------------------------------------------------------------------
  3059.  
  3060. Vsopen2:
  3061. * ワークエリアアドレスの設定
  3062. * var.vworkにその先頭アドレスが入っている
  3063.     lea    var(pc),a0
  3064.     move.l    vwork(a0),d0    * var.vwork
  3065.     add.l    vwsize(a0),d0    * +vwsize
  3066.     move.l    d0,vhash(a0)    * var.vhash=(long *)&var.vwork[var.vwsize];
  3067.     *
  3068.     moveq.l    #0,d1        * for .w = .l
  3069.     move.w    vhsize(a0),d1    * vhsize
  3070.     add.l    d1,d1
  3071.     add.l    d1,d1        * *4 for .l (vhashはlong[])
  3072.     add.l    d1,d0        * vhash[vhsize]
  3073.     lea    Vsikis(pc),a0
  3074.     move.l    d0,estack(a0)    * Vsikis.estack=(unsint *)&var.vhash[var.vhsize];
  3075.     *
  3076.     moveq.l    #0,d1        * for .w = .l
  3077.     move.w    (a0),d1        * emax
  3078.     add.l    d1,d1        * *2 for .w (estackはunsint[])
  3079.     add.l    d1,d0
  3080.     move.l    d0,vstack(a0)    * Vsikis.vstack=(long *)&Vsikis.estack[Vsikis.emax];
  3081.     *
  3082.     moveq.l    #0,d1        * for .w = .l
  3083.     move.w    vmax(a0),d1    * vmax
  3084.     add.l    d1,d1
  3085.     add.l    d1,d1        * *4 for .w (vstackはlong[])
  3086.     add.l    d1,d0
  3087.     move.l    d0,pstack(a0)    * Vsikis.pstack=(long *)&Vsikis.vstack[Vsikis.vmax];
  3088.     *
  3089.     rts
  3090.  
  3091. ******************************************************************************
  3092. *    アクセサリ 組み込み/解除/初期化
  3093. *******************************************************************************
  3094.  
  3095. DeleteAcc:
  3096. * アクセサリの解除(現在登録されているもの全て)
  3097. * 入力:a2 = ACh(内部/外部)
  3098. * 出力:d0.l = 0:ok , !=0:エラー
  3099. * 破壊:d0
  3100. regs    .reg    d1-d2/a0-a3
  3101.     movem.l    regs,-(sp)        * push regs
  3102.     moveq.l    #0,d1            * ret=0
  3103.     lea    ACdef(pc),a3        * アクセサリ構造体(内部=外部)
  3104.     lea    ACnames(pc),a1        * アクセサリ名
  3105.     moveq.l    #ACCS-1,d2        * アクセサリの数 -1 for dbra
  3106. 1:    tst.l    (a2)            * ACh[i]>=0?
  3107.     bmi    2f            * No : 未登録
  3108.     lea    MesAcc(pc),a0
  3109.     bsr    Print            * アクセサリ「
  3110.     move.l    (a1),a0
  3111.     bsr    Print            * アクセサリ名
  3112.     move.l    (a2),-(sp)        * ACh[i]
  3113.     pea    61.w
  3114.     DOS    _KNJCTRL
  3115.     addq.l    #4*2,sp
  3116.     tst.l    d0
  3117.     beq    @f            * ret=0:Ok
  3118.     * Error
  3119.     moveq.l    #1,d1            * ret=1
  3120.     lea    ErrCantDelete(pc),a0    * error
  3121.     bra    3f
  3122. @@:    * ok
  3123.     move.l    #-1,(a2)        * 未登録にする
  3124.     lea    MesDeleteOk(pc),a0    * ok message
  3125. 3:    bsr    Print
  3126. 2:    addq.l    #4,a1            * next name
  3127.     addq.l    #4,a2            * next ACh
  3128.     lea    20(a3),a3        * next ACdef
  3129.     dbra    d2,1b
  3130.     move.l    d1,d0            * ret
  3131.     movem.l    (sp)+,regs        * pop regs
  3132.     rts
  3133.  
  3134. *******************************************************************************
  3135.  
  3136. AttachAcc:
  3137. * アクセサリの登録(登録リストに従う)
  3138. * この登録前には一度全てのアクセサリが解除されていること。
  3139. * 入力:a2 = ACh内部
  3140. * 出力:d0.l = 0:ok , !=0:エラー
  3141. * 破壊:d0
  3142. regs    .reg    d1-d3/a0-a3
  3143.     movem.l    regs,-(sp)        * push regs
  3144.     * ASKのバージョンチェック
  3145.     pea    50.w
  3146.     DOS    _KNJCTRL
  3147.     addq.l    #4,sp
  3148.     cmp.l    #300,d0            * <300? (V3.00未満?)
  3149.     bcc    @f            * No (V3.00以降)
  3150.     * ASK V3.00以降でない
  3151.     lea    ErrASK3(pc),a0
  3152.     bsr    EPrint
  3153.     moveq.l    #3,d1            * return(3)
  3154.     bra    1f
  3155. *
  3156. @@:    * アクセサリの登録
  3157.     * AChの初期値は全て-1であること
  3158.     move.l    a2,d3            * ACh保存
  3159.     moveq.l    #0,d1            * ret=0
  3160.     lea    ACdef(pc),a3        * アクセサリ構造体(内部=外部)
  3161.     lea    ACnames(pc),a1        * アクセサリ名(内部=外部)
  3162.     moveq.l    #ACCS-1,d2        * アクセサリの数 -1 for dbra
  3163. 2:    lea    MesAcc(pc),a0
  3164.     bsr    Print            * アクセサリ「
  3165.     move.l    (a1),a0
  3166.     bsr    Print            * アクセサリ名
  3167.     pea    (a3)            * ACdef
  3168.     pea    60.w
  3169.     DOS    _KNJCTRL
  3170.     addq.l    #4*2,sp
  3171.     cmp.l    #-1,d0            * error?
  3172.     bne    @f            * no
  3173.     * アクセサリに登録出来ない
  3174.     lea    ErrCantAttach(pc),a0
  3175.     bsr    Print
  3176.     bsr    PrCRLF
  3177.     * 今までに登録出来たものを全て削除する
  3178.     move.l    d3,a2            * ACh復帰
  3179.     bsr    DeleteAcc
  3180.     moveq.l    #4,d1            * return(4)
  3181.     bra    1f
  3182. *
  3183. @@:    * Ok
  3184.     move.l    d0,(a2)            * ACh[i]=ret
  3185.     lea    MesAttachOk(pc),a0
  3186. 5:    bsr    Print
  3187. 3:    addq.l    #4,a1            * next name
  3188.     addq.l    #4,a2            * next ACh
  3189.     lea    20(a3),a3        * next ACdef
  3190.     dbra    d2,2b
  3191. 1:    move.l    d1,d0            * ret
  3192.     movem.l    (sp)+,regs        * pop regs
  3193.     rts
  3194.  
  3195. ******************************************************************************
  3196.  
  3197. EPrint:
  3198. * エラー出力に表示する
  3199. * 表示は全てこれで行っている
  3200. * 入力:a0 = 文字列
  3201. * 破壊:なし
  3202.     move.l    d0,-(sp)    * push d0
  3203.     move.w    #2,-(sp)    * STDERR
  3204.     pea    (a0)        * 文字列
  3205.     DOS    _FPUTS        * エラー出力へ
  3206.     addq.l    #2+4,sp
  3207.     move.l    (sp)+,d0    * pop d0
  3208.     rts
  3209.  
  3210. Print:
  3211. * 標準出力に表示する(リダイレクト可)
  3212. * 入力:a0 = 文字列
  3213. * 破壊:なし
  3214.     move.l    d0,-(sp)    * push d0
  3215.     pea    (a0)        * 文字列
  3216.     DOS    _PRINT
  3217.     addq.l    #4,sp
  3218.     move.l    (sp)+,d0    * pop d0
  3219.     rts
  3220.  
  3221. ******************************************************************************
  3222. * この中ではa0/a2は壊さないこと(プロセス管理ポインタ/コマンドラインを参照するため)
  3223.  
  3224. AMAX    equ    10    * 最大引数数
  3225.  
  3226. * コマンドライン
  3227. * a2
  3228. * 0(a2)   = コマンドライン長
  3229. * 1(a2)~ = コマンドライン
  3230. *        '-r ',0    スペース/タブはそのまま
  3231. *
  3232. GetArgv:
  3233. * コマンドラインを解析して各要素の先頭アドレスをargvに、個数をargcに格納する
  3234. * 引数:a2   = コマンドライン
  3235. * 出力:d0.w = 引数数(=argc)
  3236. * 破壊:d0-d1
  3237. regs    .reg    a2/a6
  3238.     movem.l    regs,-(sp)
  3239.     moveq.l    #0,d1        * 引数数
  3240.     tst.b    (a2)+        * コマンドライン長を飛ばす
  3241.     beq    2f        * コマンドライン長=0 -> 引数なし
  3242.     lea    argv(pc),a6
  3243. @@:    * SPC/TAB skip
  3244.     move.b    (a2)+,d0
  3245.     beq    2f        * コマンドライン終わり
  3246.     cmp.b    #SPC,d0        * skip SPC
  3247.     beq    @b
  3248.     cmp.b    #TAB,d0        * skip TAB
  3249.     beq    @b
  3250.     * SPC/TAB以外の文字が有った
  3251.     subq.l    #1,a2
  3252.     move.l    a2,(a6)+    * argv記録
  3253.     addq.w    #1,d1        * 引数+1
  3254.     cmp.w    #AMAX,d1    * 最大数を越える?
  3255.     bcc    2f        * -> 越える
  3256. 1:    * 次のEOS/SPC/TABまで飛ばす
  3257.     move.b    (a2)+,d0
  3258.     beq    2f        * コマンドライン終わり
  3259.     cmp.b    #SPC,d0        * skip SPC
  3260.     beq    @b
  3261.     cmp.b    #TAB,d0        * skip TAB
  3262.     bne    1b
  3263.     bra    @b
  3264.     *
  3265. 2:    move.w    d1,argc        * 記録
  3266.     move.w    d1,d0
  3267.     movem.l    (sp)+,regs
  3268.     rts
  3269.  
  3270. *---------------------------------------------
  3271.  
  3272. CheckOption:
  3273. * コマンドラインから指定オプションを探す
  3274. * 必ずGetArgvを呼び出した後に使うこと
  3275. * オプション名は先頭1文字だけで判別
  3276. * 引数:d2.b = オプション名(英小文字1文字/大文字の時は直後の文字列をa6に転送)
  3277. *    a6.l = 直後文字列転送エリアアドレス
  3278. * 出力:d0.l = 0:なし , !=0:そのオプションの次のアドレス
  3279. * 破壊:d0-d1
  3280. regs    .reg    d7/a4-a6
  3281.     movem.l    regs,-(sp)
  3282.     moveq.l    #0,d7        * 後ろ引数取り込まない
  3283.     cmp.b    #'a',d2        * オプション名'a'>=?
  3284.     bcc    @f        * Yes
  3285.     moveq.l    #1,d7        * 英大文字;後ろ引数取り込む
  3286.     or.b    #$20,d2        * 小文字化
  3287.     *
  3288. @@:    move.w    argc(pc),d1
  3289.     beq    1f        * 引数はない
  3290.     subq.w    #1,d1        * -1 for dbra
  3291.     lea    argv(pc),a4
  3292. @@:    move.l    (a4)+,a5    * argv[i]
  3293.     move.b    (a5)+,d0    * argv[i][0]
  3294.     * オプションの1文字目は'/''-'
  3295.     cmp.b    #'/',d0
  3296.     beq    2f
  3297.     cmp.b    #'-',d0
  3298.     beq    2f
  3299. 3:    dbra    d1,@b        * 次へ
  3300. 1:    * (指定)オプションはない
  3301.     moveq.l    #0,d0
  3302.     bra    4f
  3303.  
  3304. 2:    * '/''-'があった
  3305.     move.b    (a5)+,d0    * 次の1文字
  3306.     or.b    #$20,d0        * 英小文字化
  3307.     cmp.b    d2,d0        * 一致?
  3308.     bne    3b        * -> 不一致
  3309.     move.l    a5,d0        * オプション名の次のアドレス(!=0)
  3310.     tst.w    d7        * 後ろ取り込む?
  3311.     beq    4f        * No
  3312.     * 後ろ引数の取り込み -> a6
  3313.     * d0=a5 ; オプション名の次のアドレス(!=0)
  3314. @@:    move.b    (a5)+,d1
  3315.     beq    5f        * EOS
  3316.     cmp.b    #SPC,d1
  3317.     beq    5f
  3318.     cmp.b    #TAB,d1        * EOS/SPC/TABまで
  3319.     beq    5f
  3320.     move.b    d1,(a6)+
  3321.     bra    @b
  3322. *
  3323. 5:    clr.b    (a6)        * EOS
  3324. 4:    movem.l    (sp)+,regs
  3325.     rts
  3326.  
  3327. ******************************************************************************
  3328. *    メイン
  3329. ******************************************************************************
  3330.  
  3331.     .xref    keepchk
  3332.     .xref    Atoi
  3333.     .xref    _ChkEX68
  3334.  
  3335. main:
  3336.     lea.l    initsp(pc),sp    * PROGRAM=の時のため
  3337.     
  3338.     * タイトル表示
  3339.     move.w    #2,-(sp)    * STDERR
  3340.     pea    title(pc)    * 文字列
  3341.     DOS    _FPUTS        * エラー出力へ
  3342.     addq.l    #2+4,sp
  3343.     *
  3344.     jbsr    _ChkEX68    * EX68のチェック
  3345.     bne    Err_EX68    * 動作不可とする(将来外す可能性はある)
  3346.     *
  3347.     move.l    #(id-KEEP_START),-(sp)    * 識別子の相対位置
  3348.     pea.l    (a0)        * 自分のメモリ管理ポインタ
  3349.     bsr    keepchk        * 常駐チェック
  3350.     addq.l    #4*2,sp
  3351.     move.b    d0,d7        * d7 :0=常駐してない , -1=常駐している
  3352.     
  3353.     * 引数チェック1
  3354.     bsr    GetArgv        * argc/argv設定
  3355.     *tst.w    d0
  3356.     *beq    usage        * 引数がない -> 説明表示
  3357.     * ASKDen V2は引数なし
  3358.     moveq.l    #'r',d2        * -r : 常駐解除?
  3359.     bsr    CheckOption
  3360.     tst.l    d0
  3361.     beq    keep        * no
  3362. *
  3363. * 常駐解除
  3364. *
  3365.     tst.b    d7        * 常駐している?
  3366.     beq    Err_NoKp    * No -> error
  3367.     
  3368.     * a0=常駐しているルーチンのメモリ管理ポインタ
  3369.     * メモリー管理ポインタを飛ばし、ユーザープログラム先頭へ
  3370.     * さらに、AChまで飛ばす
  3371.     lea    fhigh-KEEP_START+PSPSIZ(a0),a4        * fhighのアドレス
  3372.     tst.b    (a4)                    * ワークは高位メモリー?
  3373.     beq    @f                    * No : 低位メモリーの時は解放ずみ
  3374.     lea    var-KEEP_START+PSPSIZ(a0),a2        * var.vwork
  3375.     move.l    (a2),-(sp)    * varのアドレス
  3376.     DOS    _MFREE        * メモリー解放
  3377.     addq.w    #4,sp
  3378.     
  3379. @@:    lea.l    ACh-KEEP_START+PSPSIZ(a0),a2        * AChのアドレス
  3380.     bsr    DeleteAcc    * アクセサリ解除
  3381.     tst.l    d0
  3382.     bne    Err_Kai        * アクセサリ登録削除不可により常駐解除不可
  3383.     *
  3384.     pea.l    MPSIZ(a0)
  3385.     DOS    _MFREE        * 自己プロセスメモリー解放
  3386.     addq.l    #4,sp
  3387.     tst.l    d0
  3388.     bmi    Err_Kai        * なぜかメモリー解放出来ない時
  3389.     *
  3390.     * 常駐解除正常終了
  3391.     lea    MesRelease(pc),a0
  3392.     bsr    Print
  3393.     clr.w    -(sp)        * exit(0)
  3394.     DOS    _EXIT2
  3395.  
  3396. keep:    * 常駐
  3397.     tst.b    d7        * 常駐している?
  3398.     bne    Err_Dbl        * Yes -> error(2重常駐)
  3399.     *
  3400.     * プログラム起動時にはフリーエリアの全てが起動プログラムに割り当てられているため、
  3401.     * これを必要部分以外解放する。そうしないとMALLOCが効かない。
  3402.     * a0=プログラムメモリ管理ポインタ
  3403.     * a1=プログラム終了アドレス+1(.data,.bssを含む)
  3404.     lea    MPSIZ(a0),a0    * メモリー管理ポインタ分を飛ばす
  3405.     move.l    a0,ProcAD    * このプロセスの先頭アドレス保存
  3406.     sub.l    a0,a1        * 当プログラムサイズ
  3407.     move.l    a1,-(sp)    * 確保する領域サイズ
  3408.     move.l    a0,-(sp)    * 確保する領域の先頭アドレス
  3409.     DOS    _SETBLOCK    * 空き領域確保
  3410.     addq.w    #4*2,sp
  3411.     tst.l    d0
  3412.     bmi    Err_Mem        * 領域が確保できない時=エラー
  3413.     *
  3414.     * 式・変数処理初期化1
  3415.     lea    work(pc),a6
  3416.     moveq.l    #'W',d2        * -Wsize : ワークエリアサイズ(size,0->(a6))
  3417.     bsr    CheckOption
  3418.     move.l    #1024,d2    * デフォルト変数領域サイズ
  3419.     tst.l    d0
  3420.     beq    @f        * サイズ指定なし
  3421.     * サイズ指定あり : サイズ読み取り
  3422.     bsr    Atoi        * 読み取り (size/sizeK) -> d0.l (d0/d1/a6破壊)
  3423.     * サイズ判定
  3424.     move.l    #256,d2        * 最小変数領域サイズ
  3425.     cmp.l    d2,d0
  3426.     bcs    @f        * <d2 -> d2
  3427.     btst.l    #0,d0        * BIT0=1? : 奇数?
  3428.     beq    11f        * No
  3429.     addq.l    #1,d0        * +1して偶数にする
  3430. 11:    move.l    d0,d2
  3431.     *
  3432. @@:    move.l    d2,-(sp)    * ワークエリアサイズ
  3433.     bsr    Vsopen1        * -> d0.l : 必要ワークエリアサイズ計算
  3434.     addq.l    #4,sp
  3435.     move.l    d0,all        * サイズ記録
  3436.     *
  3437.     move.l    d0,-(sp)    * 必要サイズ
  3438.     move.w    #2,-(sp)    * 高位メモリー
  3439.     DOS    _MALLOC2    * ワークエリア確保
  3440.     addq.l    #6,sp
  3441.     tst.l    d0
  3442.     bmi    Err_Mem        * 確保出来ない
  3443.     move.l    d0,var        * アドレス記録(var.vwork)
  3444.     *
  3445.     * アクセサリ組み込み
  3446.     lea    ACh(pc),a2
  3447.     bsr    AttachAcc
  3448.     tst.l    d0
  3449.     bne    Err_Keep    * 組み込みエラー
  3450.     *
  3451.     * アクセサリも組み込みOK
  3452.     lea    MesKeep(pc),a0
  3453.     bsr    Print
  3454.     *
  3455.     * オプション処理
  3456.     lea    preexecI(pc),a6
  3457.     clr.b    (a6)            * 指定なしの時のため
  3458.     moveq.l    #'I',d2            * -Ifname : 整数式ファイル名
  3459.     bsr    CheckOption
  3460.     *
  3461.     lea    preexecF(pc),a6
  3462.     clr.b    (a6)            * 指定なしの時のため
  3463.     moveq.l    #'F',d2            * -Ffname : 実数式ファイル名
  3464.     bsr    CheckOption
  3465.     *
  3466.     moveq.l    #'p',d2            * -p : 表示符号なし
  3467.     bsr    CheckOption
  3468.     tst.l    d0
  3469.     seq    hugo            * -pなし=符号あり
  3470.     *
  3471.     lea    work(pc),a6
  3472.     moveq.l    #'S',d2            * -Smode : 表示進数[mode=0,1,2,3]
  3473.     bsr    CheckOption
  3474.     move.l    #0,d2            * デフォルト:10進数
  3475.     tst.l    d0
  3476.     beq    @f            * 指定なし
  3477.     * 指定あり : モード読み取り
  3478.     bsr    Atoi            * 読み取り -> d0.l (d0/d1/a6破壊)
  3479.     * サイズ判定
  3480.     cmp.l    #3,d0
  3481.     bhi    @f            * >3は0とみなす
  3482.     tst.l    d0
  3483.     bmi    @f            * <0も0とみなす
  3484.     move.l    d0,d2
  3485. @@:    move.w    d2,base
  3486.     *
  3487.     move.l    #KEEP_END-KEEP_START,d6    * 基本常駐サイズ
  3488.     moveq.l    #'h',d2            * -h : 高位メモリー?
  3489.     bsr    CheckOption
  3490.     tst.l    d0
  3491.     bne    10f            * Yes
  3492.     *
  3493.     * 低位メモリーの時
  3494.     clr.b    fhigh            * 低位メモリー確保の印
  3495.     *
  3496.     * ワークエリアアドレス変更
  3497.     * このプロセスの占めるメモリー領域を拡大してワークも入るようにする
  3498.     add.l    all(pc),d6        * ワークエリアサイズ
  3499.     move.l    d6,d0
  3500.     add.l    #PSPSIZ-MPSIZ,d0    * プロセス管理ポインタ分も含める
  3501.     move.l    d0,-(sp)        * new size
  3502.     move.l    ProcAD(pc),-(sp)
  3503.     DOS    _SETBLOCK
  3504.     addq.w    #8,sp
  3505.     bmi    Err_Mem            * メモリー不足
  3506.     *
  3507.     move.l    #var,varad        * varのアドレスを記録
  3508.     *
  3509.     * ワークエリアポインターを変更
  3510.     move.l    var(pc),a2        * 元のvar.vwork
  3511.     move.l    #KEEP_END,var        * var.vworkをKEEP_ENDに変更
  3512.     *
  3513. 10:    bsr    Vsopen2            * 式・変数初期化2(アドレス設定)
  3514.     bra    InitWork
  3515. *
  3516. * エラー終了
  3517. *
  3518. Err_EX68:    * EX68上である
  3519.     lea.l    ErrEX68(pc),a0
  3520.     bra.s    error
  3521. Err_Mem:    * メモリーが不足している
  3522.     lea.l    ErrCantGetWrk(pc),a0
  3523.     bra    error
  3524. Err_NoKp:    * 常駐していないのに解除しようとした
  3525.     lea.l    NoKeep(pc),a0
  3526.     bra.s    error
  3527. Err_Dbl:    * 2重常駐
  3528.     lea.l    AlreadyKeep(pc),a0
  3529.     bra.s    error
  3530. Err_Keep:    * 常駐できない
  3531.     lea.l    CantKeep(pc),a0
  3532.     bra.s    error
  3533. Err_Kai:    * 常駐解除不可
  3534.     lea.l    CantRelease(pc),a0
  3535.     bra.s    error
  3536. usage:    * 使用法
  3537.     lea.l    MesUsage(pc),a0
  3538. error:    move.l    var(pc),d0
  3539.     beq    @f        * ワークエリアは確保されていない
  3540.     move.l    d0,-(sp)
  3541.     DOS    _MFREE        * ワークエリア解放
  3542.     addq.l    #4,sp
  3543. @@:    bsr    EPrint        * エラー出力へ表示
  3544. erRet:    move.w    #2,-(sp)    * exit(2)
  3545.     DOS    _EXIT2
  3546.  
  3547. ******************************************************************************
  3548. * メッセージなど
  3549. ******************************************************************************
  3550.  
  3551.     .even
  3552. ACnames    * メッセージアドレス表
  3553.     * アクセサリ構造体の並びと同じ
  3554.     .dc.l    MesDeni
  3555.     .dc.l    MesDenf
  3556. *
  3557. MesAcc:        .dc.b    'アクセサリ「電卓(式評価);',0
  3558. MesDeleteOk:    .dc.b    '」を削除しました',CR,LF,0
  3559. ErrCantDelete:    .dc.b    '」が削除できません',CR,LF,0
  3560. ErrCantAttach:    .dc.b    '」が登録できません',CR,LF,0
  3561. MesAttachOk:    .dc.b    '」を登録しました',CR,LF,0
  3562. ErrASK3:    .dc.b    'ASK v3/codeAではありません',CR,LF,0
  3563.  
  3564. title:        .dc.b    'ASK3/codeAアクセサリ ASKDen V2.02',CR,LF
  3565.         .dc.b    TAB,'Copyright 1998-99 by AIG-Soft',CR,LF
  3566. Eoss        .dc.b    0
  3567. MesKeep:    .dc.b    '常駐しました',CR,LF,0
  3568. MesRelease:    .dc.b    '常駐解除しました',CR,LF,0
  3569. NoKeep:        .dc.b    '常駐していません',CR,LF,0
  3570. AlreadyKeep:    .dc.b    'すでに常駐しています',CR,LF,0
  3571. CantKeep:    .dc.b    '常駐できません',CR,LF,0
  3572. CantRelease:    .dc.b    '常駐解除できません',CR,LF,0
  3573. MesUsage:    .dc.b    'ASKDen2 [/I整数式ファイル /F実数式ファイル /P /Smode /Wsize /H /R]',CR,LF,0
  3574.  
  3575. * メッセージ
  3576. ErrCantGetWrk:    .dc.b    'ワークエリアが確保できません',CR,LF,0
  3577. ErrEX68        .dc.b    'EX68上では組み込めません',CR,LF,0
  3578.  
  3579.     .even
  3580. argc        .ds.w    1        * 引数の個数
  3581. argv        .ds.l    AMAX        * 各引数の先頭アドレス
  3582.  
  3583. ******************************************************************************
  3584. * 非常駐ルーチンが使うワーク
  3585. ******************************************************************************
  3586.     .bss
  3587.     .even
  3588. ProcAD        .ds.l    1        * このプロセスの先頭アドレス
  3589. work        .ds.b    256        * コマンドライン操作
  3590.  
  3591. ******************************************************************************
  3592. * 非常駐ルーチンが使うスタック
  3593. ******************************************************************************
  3594.     .stack
  3595.     .even
  3596.     .ds.l    512
  3597. initsp:
  3598. ******************************************************************************
  3599.     .end    main
  3600.